NSThread crash[EXC_BAD_ACCESS]



下面是我的代码,包括一个线程。该线程负责队列大小,如果大小>10,则记录并删除最后一个对象。但是当我运行demo=[[myDemo-alloc]init]启动线程时,得到异常消息="EXC_BAD_ACCESS"。有人帮我解决这个问题吗?

   @interface myDemo:NSObject
    {
        NSMutableArray  *q;
        NSThread        *thread;
        bool            running;
    }
    -(void)putData:(NSData *)data;
    -(NSData *)popData;
    -(void)stopThread;
    @end;
@implementation myDemo
    -(id)init
    {
        if(NULL!=(self = [super init]))
        {
            q=[NSMutableArray array];
            thread=[[NSThread alloc] initWithTarget:self
                                           selector:@selector(myThreadMainMethod:)
                                             object:nil];
            [thread start];
        }
        return self;
    }
    -(void)myThreadMainMethod:(id)object
    {
        unsigned long count;
        NSData *data;
        if(running) return;
        running=true;
        while(running)
        {
            @synchronized(self)
            {
                count=[q count];//crash !!!!
                if(count>10)
                {
                    data=[q lastObject];
                    NSLog(@"count=%d ,remove last data=%@",count,[[[NSString alloc] initWithData:data encoding:NSUTF8StringEncoding] autorelease]);
                    [q removeLastObject];
                }
            }
        }
        running=false;
    }

putData和popData通过@synchronized(self)访问队列

-(void)putData:(NSData *)data
{
    @synchronized(self)
    {
        [q addObject:data];
    }
}
-(NSData *)popData
{
    NSData * data=NULL;
    unsigned long count;
    @synchronized(self)
    {
        count=[q count];
        if(count!=0)
        {
            data=[q lastObject];
            [q removeLastObject];
        }
    }
    return data;
}

AFAIK[NArray array]返回一个自动释放的对象。尽管我找不到这方面的参考资料。我认为您应该将其保留在init方法中,因为您没有ARC.

尝试用+1保留计数非自动释放对象初始化"q"ivar,如下所示:

- (id)init
{
    if (self = [super init])
    {
        q = [[NSMutableArray alloc] initWithCapacity:10];
        thread = [[NSThread alloc] initWithTarget:self
                                         selector:@selector(myThreadMainMethod:)
                                           object:nil];
        [thread start];
    }
    return self;
}

此外,您还必须将在后台线程上运行的所有代码放入@autoreleasepoolNSAutoreleasePool。我想你的程序不知怎么就没内存了。示例:

- (void)myThreadMainMethod:(id)object
{
    @autoreleasepool {
        static unsigned long count;
        NSData *data = nil;
        if (running) {
            return;
        }
        running = true;
        while (running)
        {
            @synchronized(self)
            {
                count=[q count];//crash !!!!
                if(count>10)
                {
                    data=[q lastObject];
                    NSLog(@"count=%d ,remove last data=%@",count,
                          [[[NSString alloc] initWithData:data
                                                 encoding:NSUTF8StringEncoding]
                          autorelease]);
                    [q removeLastObject];
                }
            }
            running=false;
        }
    }
}

此外,在你的班级中,ivar的同步也存在问题。您正在同步self,但使用的是同步范围之外的"正在运行"。此外,循环的逻辑也不清楚,你只运行了一次循环,为什么你需要它?

我如下重写线程代码。线程在"while loop"运行564次后崩溃

 -(void)myThreadMainMethod:(id)object
    {
        unsigned long count,index=0;
        NSData *data;
        NSMutableArray *q1;
        if(running) return;
        running=true;
        q1=[NSMutableArray array];
        while(running)
        {   
            @synchronized(self)
            {
                count=[q count];//crash !!!
                NSLog(@"#%d count=%d ",index++,count);
            }
        }
    }

然后我再次重写如下

-(void)myThreadMainMethod:(id)object
    {
        unsigned long count,index=0;
        NSData *data;
        NSMutableArray *q1;
        if(running) return;
        running=true;
        q1=[NSMutableArray array];
        while(running)
        {   
            @synchronized(self)
            {
                count=[q1 count];//run fine
                NSLog(@"#%d count=%d ",index++,count);       
            }
        }
    }

运行良好。。。为什么?

不是因为NSMutableArray*q1;应使用count=[q1 count];而非计数=[q计数];因为它被声明为q1而不是q???

最新更新