我有两个数组:array1
和array2
。数组的每个对象也是一个数组(2D数组)。通过这种方式,我多了他们。所以我如何使用dispatch_apply
的大数组。每次我收到不同的结果都包括正确的结果。也许有人知道如何解决它?
dispatch_apply([array2 count], queue, ^(size_t j)
{
k = 0;
for (int l = 0; l < [[array1 objectAtIndex:0] count]; l++) {
k += [[[array1 objectAtIndex:i] objectAtIndex:l] intValue] *
[[[array2 objectAtIndex:j] objectAtIndex:l] intValue];
}
kNSNumber = [NSNumber numberWithInt:k];
[multipliedArrayInto replaceObjectAtIndex:j withObject:kNSNumber];
});
[resulArray insertObject:multipliedArrayInto atIndex:i];
}
答案 0 :(得分:1)
我可以建议有两件事,我敢打赌其中一件(或两件)是解决问题的首要方法。
首先,我会在块中声明k
本地,所以毫无疑问你要覆盖它。块内的kNSNumber
可能存在同样的问题。如果您只是使用该NSNumber实例进入multipliedArrayInto
累加器,您也可以删除kNSNumber
,并在其中使用@(k)
(如果只是为了更多)可读的)。同样,请确保在multipliedArrayInto
之前声明dispatch_apply
,看起来像外部for循环(i
来自哪里)。最后,确保resulArray
被实例化,或者在外部for循环之前准备就绪。
其次,queue
是并发队列还是串行队列?如果你正在使用dispatch_apply,就像并行执行for / enumeration一样 - 我认为这很可能,所以你正在处理&#34;大数组&#34;有效 - 然后你实际上保证k
被覆盖。如果将其更改为串行,则可以按设计工作。如果你想要它是并行的,你需要在块中移动k
累加器的声明,并确保其他变量的声明也是有意义的。
更新以反映问题更新:
@antonytonies理想情况下,你在这个帖子上的后续答案应该移到问题本身,以便人们可以更容易地遵循这个主题。
所以,看起来我所描述的正是你的问题。
全局队列都是并发队列,这意味着(假设)所有调度块一次执行,k
和其他变量的内容正在逐渐消失关于块的顺序如何执行。
我已经采取了您的更新(在&#34;答案&#34;您添加了),并将其修改为可能有效:
// I renamed your method, because nameless parameters pain me. This is cosmetic, and doesn't
// matter for the problem at hand.
- (NSMutableArray *)multiplicationArrays:(NSMutableArray *)array vector:(NSMutableArray *)vector
{
// IMHO, you want to set resultArray to nil here. Another option is to set it to nil in the
// else case, below. Properties in Objective-C are initalized to nil,0,false,etc; you can
// rely on ARC to initialize pointer to objc objects on the stack, too. However, someone
// reading this code may or may not know that. IMHO, using the explicitly assignement makes it
// clear that you're going to be returning `nil` or an instance of `NSMutableArray`.
NSMutableArray *resultArray = nil;
if ([[array objectAtIndex:0] count] == [vector count]) {
// Nicely done w/ pre-allocating the result array here, so that there's no question
// of the indexes matches the results later on.
resultArray = [[NSMutableArray alloc] initWithCapacity:[array count]];
for (int i=0; i < [array count]; i++) {
[resultArray insertObject:[NSNull null] atIndex:i];
}
// 'queue' here is a concurrent queue. This means that you are proclaiming to the runtime
// that the blocks being executed are able to operate correctly w/o interference from each
// other. This is also thought of in terms of parallel execution: all these blocks may run
// **at once**. This *also* means, that you must not share storage between them.
dispatch_queue_t queue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0);
dispatch_apply([array count], queue, ^(size_t j) {
// Moved 'result' inside the block.
NSInteger result = 0;
for (int l = 0; l < [[array objectAtIndex:0] count]; l++) {
// These array reads are **NOT** thread safe. They probably don't cause must trouble in
// practice, but you may want to reconfigure this.
result += [[[array objectAtIndex:j] objectAtIndex:l] intValue] * [[vector objectAtIndex:l] intValue];
}
// The replace of the object into resultArray is **NOT** thread-safe.
// This probably hasn't caused you much trouble, since you can guarantee that
// you aren't writing at the same index. However, I would strongly suggest to
// change this to be thread-safe.
[resultArray replaceObjectAtIndex:j withObject:@(result)];
});
}
else {
NSLog(@"matrix count isn't correspond");
}
return resultArray;
}
最后:考虑使用Apple的Accelerate框架来解决这类问题。它可以在OSX和iOS上使用,因此您应该涵盖所有基础。
答案 1 :(得分:0)
-(NSMutableArray*)multiplicationArraysWithVector:(NSMutableArray *)array :(NSMutableArray *)vector
{
NSMutableArray* resultArray;
if ([[array objectAtIndex:0] count] == [vector count])
{
resultArray = [[NSMutableArray alloc] initWithCapacity:[array count]];
for (int i=0; i < [array count]; i++) {
[resultArray insertObject:[NSNull null] atIndex:i];
}
__block NSInteger result;
dispatch_queue_t queue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0);
dispatch_apply([array count], queue, ^(size_t j)
{
result = 0;
for (int l = 0; l < [[array objectAtIndex:0] count]; l++) {
result += [[[array objectAtIndex:j] objectAtIndex:l] intValue] * [[vector objectAtIndex:l]intValue];
}
[resultArray replaceObjectAtIndex:j withObject:@(result)];
});
}
else
{
NSLog(@"matrix count isn't correspond");
}
return resultArray;
}
在这种情况下,我可以获得正确或错误的数据结果。