目标C分配/释放错误

我有以下问题:

在标题中;

GDataXMLDocument *doc; NSString *xmlBody; @property (nonatomic,copy) NSString *xmlBody; @property (nonatomic,retain) GDataXMLDocument *doc; 

在米

 #import "tchLoader.h" #import "Variable.h" #import "DisplayVariable.h" @implementation tchLoader @synthesize responseXMLData,lastLoadedResponseXMLData; @synthesize conn; @synthesize doc; @synthesize xmlBody; - (void)loadXML:(id<tchLoaderDelegate>)delegate { NSString *theBaseXML= @"some xml code here" if (self.xmlBody==nil){ self.xmlBody=theBaseXML; } _delegate = delegate; /* SCNetworkReachabilityFlags flags; SCNetworkReachabilityRef reachability = SCNetworkReachabilityCreateWithName(NULL, [@"www.alues.com" UTF8String]); SCNetworkReachabilityGetFlags(reachability, &flags); // The reachability flags are a bitwise set of flags that contain the information about // connection availability BOOL reachable = ! (flags & kSCNetworkReachabilityFlagsConnectionRequired); */ NSString *soapMessage =self.xmlBody; NSURL *url = [NSURL URLWithString:@"https://area.tch-values.com/soapmwp/mws"]; NSMutableURLRequest *request = [NSMutableURLRequest requestWithURL:url]; NSString *msgLength = [NSString stringWithFormat:@"%d", [soapMessage length]]; [request addValue: @"text/xml; charset=utf-8" forHTTPHeaderField:@"Content-Type"]; [request addValue: @"http://www.tch-values.com/webservice" forHTTPHeaderField:@"SOAPAction"]; [request addValue: msgLength forHTTPHeaderField:@"Content-Length"]; [request setHTTPMethod:@"POST"]; [request setHTTPBody: [soapMessage dataUsingEncoding:NSUTF8StringEncoding]]; if ([NSURLConnection canHandleRequest:request] && true) { self.conn = [[NSURLConnection alloc ]initWithRequest:request delegate:self]; if (self.conn) { self.responseXMLData = [NSMutableData data]; } } } -(void)connection:(NSURLConnection *)connection didFailWithError:(NSError *)error { NSLog(@"ERROR with theConenction"); [self.doc release]; [self.conn release]; [self.responseXMLData release]; } - (void)connectionDidFinishLoading:(NSURLConnection *)connection { NSLog(@"DONE. Received Bytes: %d", [self.responseXMLData length]); //[self.conn release]; if ([_delegate respondsToSelector:@selector(xmlDidFinishLoading)]) { [_delegate xmlDidFinishLoading]; } } -(void)insertAnswers: (NSMutableArray*) answeredVariables{ for (Variable * variable in answeredVariables) { NSInteger pageID=[variable pageId]; //NSMutableArray *answers=[NSMutableArray arrayWithCapacity:[[variable variableValues] count]]; NSString *path = [NSString stringWithFormat:@"//inferenceresponse/state/variable[pageId=%d]/valuedefinition",pageID]; NSArray *valueElement = [doc nodesForXPath:path error:nil]; GDataXMLElement *valueDefinitionElement; if (valueElement.count > 0) { valueDefinitionElement= (GDataXMLElement *) [valueElement objectAtIndex:0]; } GDataXMLElement * sourceElement = [GDataXMLNode elementWithName:@"source"]; [sourceElement addAttribute:[GDataXMLNode attributeWithName:@"type" stringValue:@"ask user"]]; GDataXMLElement * timeStampElement = [GDataXMLNode elementWithName:@"timestamp" stringValue:@"12345"]; [sourceElement addChild:timeStampElement]; GDataXMLElement * assignmentElement = [GDataXMLNode elementWithName:@"assignmentnumber" stringValue:@"6"]; for(NSString *answer in variable.variableValues){ GDataXMLElement * variableValueElement = [GDataXMLNode elementWithName:@"variablevalue"]; [variableValueElement addAttribute:[GDataXMLNode attributeWithName:@"value" stringValue:answer]]; [valueDefinitionElement addChild:variableValueElement]; } [valueDefinitionElement addChild:sourceElement]; [valueDefinitionElement addChild:assignmentElement]; } NSData *xmlData = self.doc.XMLData; NSString *theXML = [[NSString alloc] initWithBytes:[xmlData bytes] length:[xmlData length] encoding:NSUTF8StringEncoding]; theXML =[theXML stringByReplacingOccurrencesOfString:@"inferenceresponse" withString:@"inferencerequest"]; theXML =[theXML stringByReplacingOccurrencesOfString:@"<SOAP-ENV:Envelope xmlns:SOAP-ENV=\"http://schemas.xmlsoap.org/soap/envelope/\">" withString:@"<SOAP-ENV:Envelope xmlns:xsd=\"http://www.w3.org/2001/XMLSchema\" xmlns:xsi=\"http://www.w3.org/2001/XMLSchema-instance\" xmlns:SOAP-ENC=\"http://schemas.xmlsoap.org/soap/encoding/\" SOAP-ENV:encodingStyle=\"http://schemas.xmlsoap.org/soap/encoding/\" xmlns:SOAP-ENV=\"http://schemas.xmlsoap.org/soap/envelope/\"> "]; theXML =[theXML stringByReplacingOccurrencesOfString:@"xmlns=\"\"" withString:@"xmlns=\"http://www.tch-values.com/xml/webservice\""]; theXML =[theXML stringByReplacingOccurrencesOfString:@"<state goalreached=\"false\">" withString:@"<state goalreached=\"false\"> <value>PlanKB</value> <goalvariable>myGoal</goalvariable> "]; self.xmlBody=theXML; [theXML release]; //[self.doc release]; NSLog(self.xmlBody); } - (NSMutableArray*)variablesForPageID:(NSString*)pageID { NSMutableArray *variables = nil; if (self.responseXMLData) { variables = [NSMutableArray arrayWithCapacity:10]; NSData *xmlData = self.responseXMLData; NSError *error; self.doc=nil; doc = [[GDataXMLDocument alloc] initWithData:xmlData options:0 error:&error]; if (self.doc == nil) { return nil; } NSArray *status = [doc nodesForXPath:@"//inferenceresponse/state[@goalreached='true']" error:nil]; if([status count]==1){ self.xmlBody=nil; Variable *variable=[[Variable alloc] init]; NSString *path = [NSString stringWithFormat:@"//inferenceresponse/state/displayvariables/display[@isDisplayShown='false']"]; NSArray *displayVariablesElements = [doc nodesForXPath:path error:nil]; NSMutableArray *disps=[[NSMutableArray alloc] init]; if(displayVariablesElements.count >0){ for(GDataXMLElement *disElement in displayVariablesElements){ DisplayVariable *disVar=[[DisplayVariable alloc] init]; NSArray *disPageid = [disElement nodesForXPath:@"@displayPageId" error:nil]; GDataXMLElement *Pageid = (GDataXMLElement *) [disPageid objectAtIndex:0]; disVar.displayPageId =Pageid.stringValue; NSArray *disName = [disElement nodesForXPath:@"displayname" error:nil]; if(disName.count >0){ GDataXMLElement *disNam = (GDataXMLElement *) [disName objectAtIndex:0]; disVar.displayName =disNam.stringValue; } NSArray *disValue = [disElement nodesForXPath:@"displayvalue" error:nil]; if(disValue.count >0){ GDataXMLElement *disVal = (GDataXMLElement *) [disValue objectAtIndex:0]; disVar.displayValue =disVal.stringValue; } NSArray *disId = [disElement nodesForXPath:@"@id" error:nil]; GDataXMLElement *disIdEl = (GDataXMLElement *) [disId objectAtIndex:0]; disVar.pageId =[disIdEl.stringValue intValue]; [disps addObject:disVar]; [disVar release]; } variable.displayVariables=disps; [disps release]; } variable.lastVariableofConsultation=YES; [variables addObject:variable]; [variable release]; } else{ NSArray *inferenceMembers = [doc nodesForXPath:@"//inferenceresponse/state/variable[not(valuedefinition/variablevalue)]" error:nil]; for (GDataXMLElement *variableElement in inferenceMembers) { Variable *variable=[[Variable alloc] init]; NSArray *items = [variableElement nodesForXPath:@"domaindefinition/domain/enumType/domainitem" error:nil]; NSMutableArray *domainItems = [NSMutableArray arrayWithCapacity:items.count]; for (int i=0; i<items.count;i++) { GDataXMLElement *domainItem = (GDataXMLElement *) [items objectAtIndex:i]; [domainItems addObject:domainItem.stringValue]; } variable.domainItems=domainItems; NSArray *names = [variableElement nodesForXPath:@"name/@name" error:nil]; if (names.count > 0) { GDataXMLElement *nameElement = (GDataXMLElement *) [names objectAtIndex:0]; variable.variableName = nameElement.stringValue; } NSArray *pageId = [variableElement nodesForXPath:@"pageId" error:nil]; } } return variables; } - (void)dealloc { [responseXMLData release] ; [lastLoadedResponseXMLData release] ; [conn release]; [doc release]; [xmlBody release]; [super dealloc]; } @end #import "tchLoader.h" #import "Variable.h" #import "DisplayVariable.h" @implementation tchLoader @synthesize responseXMLData,lastLoadedResponseXMLData; @synthesize conn; @synthesize doc; @synthesize xmlBody; 

如果我[theXML版本]它崩溃,如果我不释放XML然后它工作完美,但我看到模拟器仪器工具内存泄漏。 (也有很多内存泄漏,我看到在这个代码,但不能弄清instrumnets工具是怎么回事)

这看起来不对:

 [doc release]; 

为什么你释放一个属性pipe理的对象?

在您的@synthesize语句中将其更改为:

 @synthesize doc = doc_; @synthesize xmlBody = xmlBody_; 

然后修复所有产生的错误去通过属性,释放属性只在dealloc。

编辑:

你说它崩溃释放XML。 这个代码是错误的:

 NSString *theXML = [[NSString alloc] initWithBytes:[xmlData bytes] length:[xmlData length] encoding:NSUTF8StringEncoding];     theXML =[theXML stringByReplacingOccurrencesOfString:@"inferenceresponse" withString:@"inferencerequest"]; [theXML release]; 

你分配一个string,用“stringByReplacing …”调用一个自动释放的stringreplace该variables,然后尝试释放自动释放的结果string,这将会崩溃。 当你不需要在你使用的方法之后保持一个string时,总是使用autorelease。 正确的代码是:

  NSString *theXML = [[[NSString alloc] initWithBytes:[xmlData bytes] length:[xmlData length] encoding:NSUTF8StringEncoding] autorelease];     theXML =[theXML stringByReplacingOccurrencesOfString:@"inferenceresponse" withString:@"inferencerequest"]; 

拿出[XML发布] – 不会有泄漏。

我认为你应该尽可能快地使用ARC,这样可以节省很多这样的误解。

如果你想释放一个伊娃/财产(保留),这不是如何去做到这一点:

 [self.doc release]; 

代替:

 self.doc = nil; 

单身物体的一个“问题”是它们似乎泄漏。 如果你创build了一个对象而不是销毁它,仪器说这是一个泄漏,即使你的意图是从来没有释放它。

 NSData *xmlData = doc.XMLData; newXML = [[NSString alloc] initWithBytes:[xmlData bytes] length:[xmlData length] encoding:NSUTF8StringEncoding]; 

你的newXML是什么? 这是一个伊娃,并综合它,并保留它? 如果是,编译器将自动生成getter和setter方法。

 NSData *xmlData = doc.XMLData; self.newXML = [[NSString alloc] initWithBytes:[xmlData bytes] length:[xmlData length] encoding:NSUTF8StringEncoding]; self.timestamp = nil; 

如果它不属性的话

 NSString* newXML = [[NSString alloc] initWithBytes:[xmlData bytes] length:[xmlData length] encoding:NSUTF8StringEncoding]; self.xmlBody=newXML; [newXML release];