为测验应用程序创建工具栏
这与我之前发布的一个问题有关。我仍然坚持不下去。这是一个描述。我正在创建一个测验应用程序。它有一个工具栏,每次用户单击按钮时都会动态创建其按钮。我做到了使用一种方法将三个按钮添加到数组中,然后使用 for 循环检查问题的选择数量,然后为每个选择创建一个按钮并将其添加到数组中。稍后我使用
<代码> [工具栏设置项:tempArray];
添加按钮
但是在执行此操作时,我遇到了内存泄漏。该应用程序在 200 个问题后崩溃。我使用仪器发现泄漏位于按钮创建区域。但是在做了很多实验之后,我在不知道该做什么。
我还有另一个问题有
没有办法找出iphone sdk中内置方法创建的对象的保留计数。具体来说,
1)NSMutableArray的addobject方法是否会增加添加对象的保留计数 2)如果我打算释放存储在其中的customBarButtonItem对象,[[工具栏项目]释放]是否可能会造成麻烦?
因为在使用这些选项时,应用程序要么立即崩溃,要么更改对报告的泄漏没有影响,
这是代码。它有很多注释行,这是我尝试过的选项
<代码> - (void)CreateButtons{
UIToolbar *tempToolBar=[[UIToolbar alloc] ]
numberOfChoices=0;//set number of choice buttons at present to 0
NSMutableArray *tempItems=[[NSMutableArray alloc] init];//Array for holding the buttons
Question *question=[currentQuestion question];
NSString *answer=[question answerOptions];
int numericAnswer=0;
numericAnswer=[answer characterAtIndex:0];
//see if its a number or a character
if (numericAnswer > 96) { // its a character
int choice;
for (choice=97; choice <=numericAnswer ; choice ++) {
UIButton *button = [UIButton buttonWithType:UIButtonTypeCustom];
[button setBackgroundImage:[UIImage imageNamed:@"gembtnblu.png"] forState:UIControlStateNormal];
button.frame = CGRectMake(0, 0, TOOLBAR_BUTTON_WIDTH , TOOLBAR_BUTTON_HEIGHT);
[button setTitle:[NSString stringWithFormat:@"%c",(char)choice] forState:UIControlStateNormal];
[button setTitleColor:[UIColor whiteColor] forState:UIControlStateNormal];
[button addTarget:self action:@selector(ChoiceButtonTouched:) forControlEvents:UIControlEventTouchUpInside];
[button setTag:choice];
UIBarButtonItem *customBarItem = [[UIBarButtonItem alloc] initWithCustomView:button];
if (isReviewing == TRUE) {
customBarItem.customView.userInteractionEnabled=FALSE;
}
//Add button to the array
[tempItems addObject:customBarItem];
//release buttons
[customBarItem release];
numberOfChoices++;
}
}
else {
int choice;
for (choice=49; choice<=numericAnswer; choice ++) {
UIButton *button = [UIButton buttonWithType:UIButtonTypeCustom];
[button setBackgroundImage:[UIImage imageNamed:@"gembtnblu.png"] forState:UIControlStateNormal];
button.frame = CGRectMake(0, 0, TOOLBAR_BUTTON_WIDTH , TOOLBAR_BUTTON_HEIGHT);
[button setTitle:[NSString stringWithFormat:@"%c",choice] forState:UIControlStateNormal];
[button setTitleColor:[UIColor whiteColor] forState:UIControlStateNormal];
[button addTarget:self action:@selector(ChoiceButtonTouched:) forControlEvents:UIControlEventTouchUpInside];
[button setTag:choice];
UIBarButtonItem *customBarItem = [[UIBarButtonItem alloc] initWithCustomView:button];
//Add button to the array
[tempItems addObject:customBarItem];
if (isReviewing == TRUE) {
customBarItem.customView.userInteractionEnabled=FALSE;
}
//release buttons
[customBarItem release];
numberOfChoices++;
}
}
//load the image
UIButton *previousButton = [UIButton buttonWithType:UIButtonTypeCustom];
[previousButton setBackgroundImage:[UIImage imageNamed:@"prev.png"] forState:UIControlStateNormal];
[previousButton addTarget:self action:@selector(PreviousClicked:) forControlEvents:UIControlEventTouchUpInside];
previousButton.frame = CGRectMake(0, 0, TOOLBAR_BUTTON_WIDTH , TOOLBAR_BUTTON_HEIGHT);
UIBarButtonItem *customBarItem6 = [[UIBarButtonItem alloc] initWithCustomView:previousButton];
//[previousButton release];
self.prevButton=customBarItem6;
UIButton *nextButton= [UIButton buttonWithType:UIButtonTypeCustom];
[nextButton setBackgroundImage:[UIImage imageNamed:@"nex.png"] forState:UIControlStateNormal];
[nextButton addTarget:self action:@selector(nextClicked:) forControlEvents:UIControlEventTouchUpInside];
nextButton.frame = CGRectMake(0, 0, TOOLBAR_BUTTON_WIDTH, TOOLBAR_BUTTON_HEIGHT);
UIBarButtonItem *customBarItem7 = [[UIBarButtonItem alloc] initWithCustomView:nextButton];
//[nextButton release];
//Use this to put space in between your toolbox buttons
UIBarButtonItem *flexItem = [[UIBarButtonItem alloc] initWithBarButtonSystemItem:UIBarButtonSystemItemFlexibleSpace target:nil action:nil];
[tempItems addObject:flexItem];
[tempItems addObject:customBarItem6];
[tempItems addObject:customBarItem7];
//release buttons
[customBarItem6 release];
[customBarItem7 release];
[flexItem release];
//NSArray *items=[[NSArray alloc] initWithArray:(NSArray *)tempItems];
//[tempItems release];
//add array of buttons to toolbar
//if([[toolbar items] count]>0)
// { // [[工具栏项目]释放]; // } [工具栏 setItems:tempItems 动画:YES]; //[物品发布]; //[self.view addSubview:工具栏]; if(isReviewing == FALSE &&isPractice == FALSE) {
prevButton.enabled=FALSE;
}
//[toolbar bringSubviewToFront:customBarItem6.customView];
}
工具栏是通过 ib 创建的
是的,它有很多代码,但它只是根据问题的选择数量创建按钮。两个 for 循环类似,除了一个将 a、b、c、d 放在按钮上,而另一种则放置 1,2,3,4.....此外还创建了三个按钮。一个用于下一个、上一个和弹性项目。每次用户单击下一个按钮时都会调用此方法。
This is related to a question i posted earlier.I am still stuck on it.Heres a description.I am creating a quiz app.It has a toolbar whose buttons are to be created dynamicaly each time the user clicks a button.I did it using a method which adds three buttons into an arrray, then uses a for loop to check the number of choices the question has and then create and add a button to the array for each choice.Later i use
[toolbar setitems:tempArray];
to add the buttons
But while doing this i am running into memory leaks.The app crashes after 200 questions.I found using instruments that the leaks were in button creation area.But after doing many experiments im at a loss about what to do.
I also have another question
Is there a way to find out the retain count of objects created by built in methods in iphone sdk.Specificaly,
1)Does NSMutableArray's addobject method increase the retain count of the added object
2)Is [[toolbar items] release] likely to cause trouble if i am intending to release the customBarButtonItem objects stored in it?
because wile playing with these options , the app either crashes immediately or the changes have no effect on the reported leaks
heres the code.Its got a lot of comment lines which are options i tried
- (void)CreateButtons{
UIToolbar *tempToolBar=[[UIToolbar alloc] ]
numberOfChoices=0;//set number of choice buttons at present to 0
NSMutableArray *tempItems=[[NSMutableArray alloc] init];//Array for holding the buttons
Question *question=[currentQuestion question];
NSString *answer=[question answerOptions];
int numericAnswer=0;
numericAnswer=[answer characterAtIndex:0];
//see if its a number or a character
if (numericAnswer > 96) { // its a character
int choice;
for (choice=97; choice <=numericAnswer ; choice ++) {
UIButton *button = [UIButton buttonWithType:UIButtonTypeCustom];
[button setBackgroundImage:[UIImage imageNamed:@"gembtnblu.png"] forState:UIControlStateNormal];
button.frame = CGRectMake(0, 0, TOOLBAR_BUTTON_WIDTH , TOOLBAR_BUTTON_HEIGHT);
[button setTitle:[NSString stringWithFormat:@"%c",(char)choice] forState:UIControlStateNormal];
[button setTitleColor:[UIColor whiteColor] forState:UIControlStateNormal];
[button addTarget:self action:@selector(ChoiceButtonTouched:) forControlEvents:UIControlEventTouchUpInside];
[button setTag:choice];
UIBarButtonItem *customBarItem = [[UIBarButtonItem alloc] initWithCustomView:button];
if (isReviewing == TRUE) {
customBarItem.customView.userInteractionEnabled=FALSE;
}
//Add button to the array
[tempItems addObject:customBarItem];
//release buttons
[customBarItem release];
numberOfChoices++;
}
}
else {
int choice;
for (choice=49; choice<=numericAnswer; choice ++) {
UIButton *button = [UIButton buttonWithType:UIButtonTypeCustom];
[button setBackgroundImage:[UIImage imageNamed:@"gembtnblu.png"] forState:UIControlStateNormal];
button.frame = CGRectMake(0, 0, TOOLBAR_BUTTON_WIDTH , TOOLBAR_BUTTON_HEIGHT);
[button setTitle:[NSString stringWithFormat:@"%c",choice] forState:UIControlStateNormal];
[button setTitleColor:[UIColor whiteColor] forState:UIControlStateNormal];
[button addTarget:self action:@selector(ChoiceButtonTouched:) forControlEvents:UIControlEventTouchUpInside];
[button setTag:choice];
UIBarButtonItem *customBarItem = [[UIBarButtonItem alloc] initWithCustomView:button];
//Add button to the array
[tempItems addObject:customBarItem];
if (isReviewing == TRUE) {
customBarItem.customView.userInteractionEnabled=FALSE;
}
//release buttons
[customBarItem release];
numberOfChoices++;
}
}
//load the image
UIButton *previousButton = [UIButton buttonWithType:UIButtonTypeCustom];
[previousButton setBackgroundImage:[UIImage imageNamed:@"prev.png"] forState:UIControlStateNormal];
[previousButton addTarget:self action:@selector(PreviousClicked:) forControlEvents:UIControlEventTouchUpInside];
previousButton.frame = CGRectMake(0, 0, TOOLBAR_BUTTON_WIDTH , TOOLBAR_BUTTON_HEIGHT);
UIBarButtonItem *customBarItem6 = [[UIBarButtonItem alloc] initWithCustomView:previousButton];
//[previousButton release];
self.prevButton=customBarItem6;
UIButton *nextButton= [UIButton buttonWithType:UIButtonTypeCustom];
[nextButton setBackgroundImage:[UIImage imageNamed:@"nex.png"] forState:UIControlStateNormal];
[nextButton addTarget:self action:@selector(nextClicked:) forControlEvents:UIControlEventTouchUpInside];
nextButton.frame = CGRectMake(0, 0, TOOLBAR_BUTTON_WIDTH, TOOLBAR_BUTTON_HEIGHT);
UIBarButtonItem *customBarItem7 = [[UIBarButtonItem alloc] initWithCustomView:nextButton];
//[nextButton release];
//Use this to put space in between your toolbox buttons
UIBarButtonItem *flexItem = [[UIBarButtonItem alloc] initWithBarButtonSystemItem:UIBarButtonSystemItemFlexibleSpace target:nil action:nil];
[tempItems addObject:flexItem];
[tempItems addObject:customBarItem6];
[tempItems addObject:customBarItem7];
//release buttons
[customBarItem6 release];
[customBarItem7 release];
[flexItem release];
//NSArray *items=[[NSArray alloc] initWithArray:(NSArray *)tempItems];
//[tempItems release];
//add array of buttons to toolbar
//if([[toolbar items] count]>0)
// {
// [[toolbar items] release];
// }
[toolbar setItems:tempItems animated:YES];
//[items release];
//[self.view addSubview:toolbar];
if(isReviewing == FALSE && isPractice == FALSE) {
prevButton.enabled=FALSE;
}
//[toolbar bringSubviewToFront:customBarItem6.customView];
}
toolbar is created via ib
Yeah its a lot of code but it just creates buttons based on number of choices for a question.The two for loops are similar exept one puts a,b,c,d on the buttons while the other one puts 1,2,3,4.....In addition three buttons are created.One for next, previous and a flex item .This method is is called each time the user clicks teh next button.
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(2)
我可以看到一些在内存方面效率不高的事情:
buttonWithType
和 'imageNamed`。这些将在未来的某个时刻自动释放,但不会在您的方法内。tempToolbar
项已分配但从未释放。这会泄漏。tempItems
似乎也没有被释放:这将彻底杀死您,因为所有按钮都添加到其中...基于此,我建议:
祝你好运
I can see a few things which are not very efficient memory-wise:
buttonWithType
and 'imageNamed`. These will autorelease themselves at some point in the future but not within your method.tempToolbar
is allocated but never released. This will leak.tempItems
also does not appear to be released: this will kill you completely since all your buttons are added to it...Based on this I would suggest:
NSAutoReleasePool
at the start of your method anddrain
it at the end: this will release all autoreleased entities.Good luck
很难理解所有这些代码,但是 1) 的一个简单的部分答案是,是的,
[NSMutableArray addObject:]
增加了保留+1。Difficult to follow all that code, but an easy part-answer to 1) is that, yes,
[NSMutableArray addObject:]
increase retain +1.