【发布时间】:2014-11-07 10:35:30
【问题描述】:
在我的 android 应用程序中,我有 LinkedBlockingQueue 的 HashMap:
private ConcurrentHashMap<Integer, LinkedBlockingQueue<short[]>> mBuffer = new ConcurrentHashMap<Integer, LinkedBlockingQueue<short[]>>(8,0.9f,1);
每个键都有单独的线程生成数据。数据以这种方式添加:
public void addFrameCopy(Integer sampleId, short[] frame) {
LinkedBlockingQueue<short[]> value;
if (!mBuffer.containsKey(id)) {
value= new LinkedBlockingQueue<short[]>();
mBuffer.put(id, value);
} else {
value = mBuffer.get(sampleId);
}
Log.d("IN "+id,inCounter+" "+getShortArraySum(frame)+"");
inCounter++;
value.add(Arrays.copyOf(frame,frame.length));
}
所有键都有一个消费者线程。消费是这样运作的:
public List<Pair<ControlFrame, short[]>> getCombinedFramesBatchSkipWhenNeeded
(List<Pair<Integer, ControlFrame>> controlFrames,
List<Pair<ControlFrame, short[]>> out) {
Set<Integer> nonUsedKeys = mBuffer.keySet();
LinkedBlockingQueue<short[]> list;
short[] takenDataFrame;
for (Pair<Integer, ControlFrame> controlPair : controlFrames) {
if (shouldSatisfyControlFrame(controlPair.second)) {
list=mBuffer.get(controlPair.first);
try {
takenDataFrame = list.take();
} catch (InterruptedException e) {
e.printStackTrace();
continue;
}
Pair<ControlFrame, short[]> combinedFrame = new Pair<ControlFrame, short[]>(controlPair.second, takenDataFrame);
Log.d("OUT "+controlPair.first,outCounter+" "+getShortArraySum(takenDataFrame)+"");
outCounter++;
out.add(combinedFrame);
nonUsedKeys.remove(controlPair.first);
} else {
attemptToSkipFrames(controlPair);
}
}
for (Integer key : nonUsedKeys) {
Log.d("OUT "+key,"Skip");
list=mBuffer.get(key);
if(!list.isEmpty())
list.remove(0);
}
return out;
}
从不调用方法 attemptToSkipFrames。 我正在为一个生产线程运行测试。这是我得到的日志:
IN 9﹕ 0 0
OUT 9﹕ 0 0
IN 9﹕ 1 26494
OUT 9﹕ 1 26494
IN 9﹕ 2 203342
IN 9﹕ 3 -427941
IN 9﹕ 4 31709
OUT 9﹕ 2 203342
IN 9﹕ 5 457126
OUT 9﹕ 3 457126
看起来没有。 2是清单,导致拿不到。 3 将值插入为否。 5. 如何防止丢失物品?
简化
用于在没有 hashmap 代码的情况下插入和获取数据的方法。
public void addFrameCopy(Integer sampleId, short[] frame) {
LinkedBlockingQueue<short[]> value=getQueue(sampleId);
Log.d("IN "+id,inCounter+" "+getShortArraySum(frame)+"");
inCounter++;
value.add(Arrays.copyOf(frame,frame.length));
}
public List<Pair<ControlFrame, short[]>> getCombinedFramesBatchSkipWhenNeeded
(List<Pair<Integer, ControlFrame>> controlFrames,
List<Pair<ControlFrame, short[]>> out) {
LinkedBlockingQueue<short[]> list;
short[] takenDataFrame;
for (Pair<Integer, ControlFrame> controlPair : controlFrames) {
list=getQueue(controlPair.first);
try {
takenDataFrame = list.take();
} catch (InterruptedException e) {
e.printStackTrace();
continue;
}
Pair<ControlFrame, short[]> combinedFrame = new Pair<ControlFrame, short[]>(controlPair.second, takenDataFrame);
Log.d("OUT "+controlPair.first,outCounter+" "+getShortArraySum(takenDataFrame)+"");
outCounter++;
out.add(combinedFrame);
}
return out;
}
【问题讨论】:
-
这看起来有点复杂,尝试减少代码以便更容易复制
-
我添加了删除了 hashmap 逻辑的代码,现在够清楚了吗?
-
我试着看了一下,但是缺少的代码太多了。尝试创建一个真正运行并演示问题的单类版本(根据需要使用内部类)。为了使其更适合,请尽可能避免使用空行。
-
找到了!我至少欠你一杯啤酒拉尔夫
标签: java android multithreading concurrency queue