0

我创建了一个 NSMutableArray,只要我的应用程序存在就需要它,我们称之为 suseranArray,就在我的主类的 @implementation 之后。该数组将包含一个名为 Vassal 的类的多个对象。封臣很简单:

1) 一个 NSMutableString 2) 另一个 NSMutableString 3) 一个 NSMutableArray 4) 另一个 NSMutable 数组

应用程序的生命周期也需要创建的每个封臣,并且它们永远不会改变。

这些对象在 .h 文件中作为(保留)属性,在 .m 文件中合成,并且每当在 init 函数期间创建对象 Vassal 时,每个对象都会被赋予一个 alloc+init。每个附庸都有数据填充并存储在宗主数组中。第三项总是有几个元素,在出现错误后,我放一行检查它是否为空,但从来没有,生活是美好的。

现在,稍后当需要某个 Vassal 对象时,我们尝试访问它的第三个属性以获取其中的数据,有时该数组为空……我检查它是否以某种方式消失了,但它总是在调试,携带一个像 0x2319f8a0 这样的好地址,这是有道理的,因为它上面的 NSMutableString 位于地址 0x2319fb40 - (经过很多头痛后,我期待 00000000)。怎么了?我的脑袋,我正在创建一个 RETAINed 对象,它保留默认放入的数据,并且该对象被放入另一个对象中,但是数组中的数据不知何故消失了。什么可能的情况会导致这种情况?感谢您的时间 :)

注意:在这个开发阶段,最后一个数组目前只包含一项,奇怪的是,尽管这两个数组是“兄弟”,但永远不会丢失一项

Vassal.h
@interface Vassal : NSObject
@property  (retain) NSMutableString *wordBody;
@property  (retain) NSMutableString *wordCode;
@property   (retain) NSMutableArray *wordRelations;
@property   (retain) NSMutableArray *wordLinks;
@end

Vassal.m
@implementation Vassal:NSObject
@synthesize wordBody;
@synthesize wordCode;
@synthesize wordRelations;
@synthesize wordLinks;
-(NSObject*) init
{
    if(self=[super init])
    {
        wordBody=[[NSMutableString alloc] init];
        wordCode=[[NSMutableString alloc] init];
        wordRelations=[[NSMutableArray alloc] init];
        wordLinks=[[NSMutableArray alloc] init];
    }
    return self;
}

//Somewhere in Suseran:
-(void)fillStuff
{
    ...
    Vassal *vassal=[Vassal new];
    for (int i=0;i<[originalDataString length];i++)
    {
        ...
        [vassal.wordRelations addObject:anItem];
        ...
    }
    int errorTest=[vassal.wordRelations count];
    if (errorTest==0)
    {
         //breakpoint here. Program NEVER comes here
    }
    [bigArrayOfVassals addObject:vassal];
}
//these arrays are never touched again but here:
-(void) getVassalstuff:(NSMutableString*)codeOfDesiredVassal
{
    Vassal *aVassal;
    for (int i=0;i<[bigArrayOfVassals count];i++)
    {
            aVassal=bigArrayOfVassals[i];
            if ([codeOfDesiredVassal isEqualToString:aVassal.wordCode)
            {
                  int errorTest=[aVassal.wordRelations count];
                  if (errorTest==0)
                  {
                         //yay! this breakpoint sometimes is hit, sometimes not,
                         //depending on code's mood. Why is this happening to me? :,(
                  }
            }
    }
}
4

1 回答 1

1

我看到您拥有可变的属性(除了特定情况,这本身就是一个坏主意)并且您正在保留它们。

可变性意味着如果您将数组设置为基于其他数组的属性,并且如果更改了原始数组,则属性中的数组也会更改。可能是因为您没有显示任何代码,所以我不知道您正在清空原始数组,从而更改您作为属性的数组

解决方案:

我首选的解决方案是为您的属性使用这些类的不可变版本;NSString、NSArray 而不是保留使用副本

第二种解决方案是将属性保留为可变的,但为每个属性编写一个自定义设置器,用于存储mutableCopy您传入的对象的一个​​。

在这两种情况下,您的属性将是用于设置属性的对象的副本,因此如果对象在您的类之外更改,它不会影响您的类的属性。

编辑添加,评论后

如果您将您的财产声明为

@property (copy) NSArray wordRelations;

然后简单地写

vassal wordArray = tempArray;

会做同样的事情,并且更干净,更具可读性..

于 2013-08-22T00:38:43.903 回答