Iphone 如何在NSMutableArray中交换值?

Iphone 如何在NSMutableArray中交换值?,iphone,objective-c,nsmutablearray,Iphone,Objective C,Nsmutablearray,这段代码是我的错,知道为什么吗allButtons是一个NSMutableArray,它包含3个对象,a=0,b=1,a和b是int类型 if(a != -1 && b!= -1){ //Swap index in "allButtons" id tempA = [allButtons objectAtIndex:a]; id tempB = [allButtons objectAtIndex:b]; [allButtons replaceObj

这段代码是我的错,知道为什么吗
allButtons
是一个
NSMutableArray
,它包含3个对象,
a=0,b=1
,a和b是
int
类型

 if(a != -1 && b!= -1){
    //Swap index in "allButtons"
    id tempA = [allButtons objectAtIndex:a];
    id tempB = [allButtons objectAtIndex:b];
    [allButtons replaceObjectAtIndex:a withObject:tempB]; //Seg fault here?????
    [allButtons replaceObjectAtIndex:b withObject:tempA];
    needLoad = false;
    [self setUpButtons];
 }
编辑:


tempA
将在调用第一个
replaceObjectAtIndex
时释放。打电话时请记住这一点。。。我不知道为什么发布
tempA
会给您带来麻烦,检查一下它的
dealloc
功能

检查
tempA
的retain计数,以验证调用
replaceObjectAtIndex
确实解除了它(而不是简单地解除了它),如下所示:

id tempA = [allButtons objectAtIndex:a];
NSLog(@"retain count for tempA: %i", [tempA retainCount]);

如果在该级别看到retain计数为1,则对象
tempA
将通过调用
replaceObjectAtIndex
解除锁定。第一次调用
replaceObjectAtIndex:
将释放旧对象(
tempA
),但这不会导致seg故障。正如@Zoran所提到的,尝试记录tempA的
retainCount
,并验证其计数


同样,对于交换数组中的元素,应该使用而不是
replaceObjectAtIndex:withObject
。iPhone 2.0支持此功能。

请阅读并理解上的可可规则。请注意,您尚未声明对tempA和tempB引用的对象的所有权,因此必须注意以下事项:

通常保证接收到的对象在其接收到的方法内保持有效。。。(不过,如果修改从中接收到另一个对象的对象,也必须小心)。该方法还可以安全地将对象返回给其调用程序

基本上,线路:

[allButtons replaceObjectAtIndex:a withObject:tempB];
可能导致tempA被解除分配。这意味着后续行将导致allButtons向无效对象发送retain消息,从而导致seg故障。要解决此问题,您需要在交换之前保留tempA,然后释放它或在交换之后自动释放它


注意:忘记保留计数是明智的。除非您完全了解所有接触对象的对象的实现,否则无法对对象的保留计数进行任何假设。例如,没有规则规定NSMutableArray的实现只会保留其元素一次。

正如您所说

NSMutableArray *allbuttons = // something
这并不意味着它一定是一个NSMutableArray,它只是意味着编译器认为它将是一个NSMutableArray

如果它来自CoreData,那么它可能只是一个
NSArray
,因此您尝试的方法调用将不起作用-您将得到未聚合的选择器或类似的东西

您必须首先将其转换为可变数组

NSArray *coreData = // core data call

// Create a mutable copy
// NB This means that you are now working on a copy, not the original :)
NSMutableArray *allButtons = [coreData mutableCopy];

使用此方法传递适当的索引

exchangeObjectAtIndex:withObjectAtIndex: 

我尝试了
exchangeObjectAtIndex:withObjectAtIndex
,这就是我得到的
由于未捕获的异常“NSInvalidArgumentException”而终止应用程序的原因:'***-[\u PFArray exchangeObjectAtIndex:withObjectAtIndex:]:未识别的选择器发送到实例0x3a35a30'
。顺便说一句,
recontcount
returnback3.您使用的是什么版本的iPhone SDK?另外,请在创建
NSMutableArray
的地方发布代码,并使用
exchangeObject..
看起来
\PFArray
NSArray
的子类,没有
NSMutableArray
的方法。您可能需要创建一个类型为
NSMutableArray
的新对象,并使用现有数组对其进行初始化
NSMutableArray*theObject=[NSMutableArray Array WithArray:allButtons]
然后调用
theObject
上的
ExchangeObject..
。()这也解释了为什么
replaceObjectAtIndex
以前是seg故障。实际上,这已经修复了它,我如何将它存储回
allButtons
recontcount
return back 3。您是从主线程还是从辅助线程调用它?如果是从辅助线程调用,是否创建了自动释放池?如果可能,发布实际错误消息可能会有所帮助。发布类声明可能也会有帮助,这样我们就可以看到allButtons是否是属性,如果是,它的内存管理语义是什么,等等,或者只是NSMutableArray*allButtons=[coreData mutablecopy];
exchangeObjectAtIndex:withObjectAtIndex: