Iphone 将数据从NSObject发送到UIViewController
我已经研究这个问题将近4天了 我认为这不是我的代码的问题,而是引起问题的应用程序的结构 我正在尝试实现协议和委托,以将数组从一个NSObject(类)获取到一个ViewController 我的代码几乎是逐行复制而来的。唯一的区别在于我打开的面,因此不得不将(非原子,保留)替换为(强),并且没有使用dealloc:) 尽管如此,它仍然没有将数据传回viewcontroller。(非常烦人)我尝试了几十种不同的解决方案组合,但都没有奏效。这让我相信,我的应用程序的结构或初始化方式可能存在错误,我现在将尝试解释一下 当带有tableview的viewcontroller加载名为parser类委托的viewdidload方法时,tableview的第一个单元格加载后,它将调用我的连接类,并告诉它从服务器下载一些数据。 在我的connection类中,我使用apple库中的NSURLConnection委托,在委托方法ConnectionDiFinishLoading中,下载的数据被传递到我的解析器类(然而,我认为这是出错的地方,因为我再次声明了对象..我认为这就是出错的地方) 这就是我从连接类调用解析器类的方式Iphone 将数据从NSObject发送到UIViewController,iphone,ios,delegates,protocols,Iphone,Ios,Delegates,Protocols,我已经研究这个问题将近4天了 我认为这不是我的代码的问题,而是引起问题的应用程序的结构 我正在尝试实现协议和委托,以将数组从一个NSObject(类)获取到一个ViewController 我的代码几乎是逐行复制而来的。唯一的区别在于我打开的面,因此不得不将(非原子,保留)替换为(强),并且没有使用dealloc:) 尽管如此,它仍然没有将数据传回viewcontroller。(非常烦人)我尝试了几十种不同的解决方案组合,但都没有奏效。这让我相信,我的应用程序的结构或初始化方式可能存在错误,我现
parserClass *myparser = [[EngineResponses alloc] init];
[myparser ReciveResponse:receivedData];
一旦数据进入我的解析器类,它就会被解析,然后我尝试将数据传递给我的viewcontroller。。但它从不访问我设置的委托方法
希望这就是问题所在,因为我不知道还有什么地方出了问题。
你觉得怎么样
更新:这是我的代码-
ViewController.h
#import "EngineResponses.h" //delegates & protocols
interface SearchViewController : UITableViewController <PassParsedData> {
//delegates to parser class
EngineResponses *engineResponses;
//..
@protocol PassParsedData
- (void)sendArray:(NSArray *)array;
@end
//..
id <PassParsedData> mydelegate;
//..
@property (strong) id <PassParsedData> mydelegate;
#import "EngineResponses.h" //delegates & protocols
interface SearchViewController : UITableViewController <PassParsedData> {
//delegates to parser class
EngineResponses *engineResponses;
EngineRequests *engineRequests;
//..
EngineResponses *engineResponses;
@protocol PassParsedData
- (void)sendArray:(NSArray *)array;
@end
//..
id <PassParsedData> mydelegate;
//..
@property (strong) id <PassParsedData> mydelegate;
EngineRequests.m
#import "EngineResponses.h"
//this is where I set up the delegate/protocol for the parser class
- (void)viewDidLoad
{
[super viewDidLoad];
//..
engineResponses = [[EngineResponses alloc] init];
[engineResponses setMydelegate:self];
//..
}
//this is where i set up and call the connection class
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
//..
if(indexPath.section == 0){
//..
if (indexPath.row == 0){
EngineRequests *engineRequests = [[EngineRequests alloc] init];
[engineRequests initalizePacketVariables:0 startCode:@"myReg" activationCode:@"myAct" methodName:@"GetStuff"];
//..
}
#pragma - Reciver methods
- (void)sendArray:(NSArray *)array
{
ICMfgFilterArray = array;
[self.tableView reloadData];
}
//connection delegates etc..
//then I pass the data from the connection delegates over to the parser class
- (void)connectionDidFinishLoading:(NSURLConnection *)connection
{
EngineResponses *engineResponses = [[EngineResponses alloc] init];
[engineResponses ReciveResponse:receivedData];
}
- (void)parserDidEndDocument:(NSXMLParser *)parser
{
//..
[[self mydelegate]sendArray:filteredArray];
}
#import "EngineResponses.h"
//this is where I set up the delegate/protocol for the parser class
- (void)viewDidLoad
{
[super viewDidLoad];
//..
engineResponses = [[EngineResponses alloc] init];
[engineResponses setMydelegate:self];
engineRequests = [[EngineRequests alloc] init]; // Use instance variable instead of local variable
[engineRequests setEnineResponses:engineResponses];
//..
}
//this is where i set up and call the connection class
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
//..
if(indexPath.section == 0){
//..
if (indexPath.row == 0){
[engineRequests initalizePacketVariables:0 startCode:@"myReg" activationCode:@"myAct" methodName:@"GetStuff"];
//..
}
#pragma - Reciver methods
- (void)sendArray:(NSArray *)array
{
ICMfgFilterArray = array;
[self.tableView reloadData];
}
@synthesize engineResponses;
//connection delegates etc..
//then I pass the data from the connection delegates over to the parser class
- (void)connectionDidFinishLoading:(NSURLConnection *)connection
{
//EngineResponses *engineResponses = [[EngineResponses alloc] init]; //This Object has already been created!
[engineResponses ReciveResponse:receivedData];
}
- (void)parserDidEndDocument:(NSXMLParser *)parser
{
//..
[[self mydelegate]sendArray:filteredArray];
}
引擎响应。h
#import "EngineResponses.h" //delegates & protocols
interface SearchViewController : UITableViewController <PassParsedData> {
//delegates to parser class
EngineResponses *engineResponses;
//..
@protocol PassParsedData
- (void)sendArray:(NSArray *)array;
@end
//..
id <PassParsedData> mydelegate;
//..
@property (strong) id <PassParsedData> mydelegate;
#import "EngineResponses.h" //delegates & protocols
interface SearchViewController : UITableViewController <PassParsedData> {
//delegates to parser class
EngineResponses *engineResponses;
EngineRequests *engineRequests;
//..
EngineResponses *engineResponses;
@protocol PassParsedData
- (void)sendArray:(NSArray *)array;
@end
//..
id <PassParsedData> mydelegate;
//..
@property (strong) id <PassParsedData> mydelegate;
1好的。我将根据您更新的代码重新执行此操作。为了方便起见,我复制了您的代码并进行了修改 ViewController.h
#import "EngineResponses.h" //delegates & protocols
interface SearchViewController : UITableViewController <PassParsedData> {
//delegates to parser class
EngineResponses *engineResponses;
//..
@protocol PassParsedData
- (void)sendArray:(NSArray *)array;
@end
//..
id <PassParsedData> mydelegate;
//..
@property (strong) id <PassParsedData> mydelegate;
#import "EngineResponses.h" //delegates & protocols
interface SearchViewController : UITableViewController <PassParsedData> {
//delegates to parser class
EngineResponses *engineResponses;
EngineRequests *engineRequests;
//..
EngineResponses *engineResponses;
@protocol PassParsedData
- (void)sendArray:(NSArray *)array;
@end
//..
id <PassParsedData> mydelegate;
//..
@property (strong) id <PassParsedData> mydelegate;
说明:EngineRequests现在是一个实例变量,不应在本地重新定义。
您可以在本地定义一个相同名称的变量,该变量将隐藏实例变量。我想
在这种情况下,您会得到一个编译器警告,但这会起作用,并且很可能会让您感到困惑。
同样,如果您一次使用多个请求,那么此解决方案将不起作用
引擎请求.h
#import "EngineResponses.h" //delegates & protocols
interface SearchViewController : UITableViewController <PassParsedData> {
//delegates to parser class
EngineResponses *engineResponses;
//..
@protocol PassParsedData
- (void)sendArray:(NSArray *)array;
@end
//..
id <PassParsedData> mydelegate;
//..
@property (strong) id <PassParsedData> mydelegate;
#import "EngineResponses.h" //delegates & protocols
interface SearchViewController : UITableViewController <PassParsedData> {
//delegates to parser class
EngineResponses *engineResponses;
EngineRequests *engineRequests;
//..
EngineResponses *engineResponses;
@protocol PassParsedData
- (void)sendArray:(NSArray *)array;
@end
//..
id <PassParsedData> mydelegate;
//..
@property (strong) id <PassParsedData> mydelegate;
EngineRequests.m
#import "EngineResponses.h"
//this is where I set up the delegate/protocol for the parser class
- (void)viewDidLoad
{
[super viewDidLoad];
//..
engineResponses = [[EngineResponses alloc] init];
[engineResponses setMydelegate:self];
//..
}
//this is where i set up and call the connection class
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
//..
if(indexPath.section == 0){
//..
if (indexPath.row == 0){
EngineRequests *engineRequests = [[EngineRequests alloc] init];
[engineRequests initalizePacketVariables:0 startCode:@"myReg" activationCode:@"myAct" methodName:@"GetStuff"];
//..
}
#pragma - Reciver methods
- (void)sendArray:(NSArray *)array
{
ICMfgFilterArray = array;
[self.tableView reloadData];
}
//connection delegates etc..
//then I pass the data from the connection delegates over to the parser class
- (void)connectionDidFinishLoading:(NSURLConnection *)connection
{
EngineResponses *engineResponses = [[EngineResponses alloc] init];
[engineResponses ReciveResponse:receivedData];
}
- (void)parserDidEndDocument:(NSXMLParser *)parser
{
//..
[[self mydelegate]sendArray:filteredArray];
}
#import "EngineResponses.h"
//this is where I set up the delegate/protocol for the parser class
- (void)viewDidLoad
{
[super viewDidLoad];
//..
engineResponses = [[EngineResponses alloc] init];
[engineResponses setMydelegate:self];
engineRequests = [[EngineRequests alloc] init]; // Use instance variable instead of local variable
[engineRequests setEnineResponses:engineResponses];
//..
}
//this is where i set up and call the connection class
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
//..
if(indexPath.section == 0){
//..
if (indexPath.row == 0){
[engineRequests initalizePacketVariables:0 startCode:@"myReg" activationCode:@"myAct" methodName:@"GetStuff"];
//..
}
#pragma - Reciver methods
- (void)sendArray:(NSArray *)array
{
ICMfgFilterArray = array;
[self.tableView reloadData];
}
@synthesize engineResponses;
//connection delegates etc..
//then I pass the data from the connection delegates over to the parser class
- (void)connectionDidFinishLoading:(NSURLConnection *)connection
{
//EngineResponses *engineResponses = [[EngineResponses alloc] init]; //This Object has already been created!
[engineResponses ReciveResponse:receivedData];
}
- (void)parserDidEndDocument:(NSXMLParser *)parser
{
//..
[[self mydelegate]sendArray:filteredArray];
}
说明:这里对EngineResponses的引用现在也是一个实例变量,而不是本地定义的变量。对象不会是新创建的,但它引用了在视图控制器中创建的对象。这是EngineResponse“知道”其视图控制器对象的一个,因此可以传回解析的数据
引擎响应。h
#import "EngineResponses.h" //delegates & protocols
interface SearchViewController : UITableViewController <PassParsedData> {
//delegates to parser class
EngineResponses *engineResponses;
//..
@protocol PassParsedData
- (void)sendArray:(NSArray *)array;
@end
//..
id <PassParsedData> mydelegate;
//..
@property (strong) id <PassParsedData> mydelegate;
#import "EngineResponses.h" //delegates & protocols
interface SearchViewController : UITableViewController <PassParsedData> {
//delegates to parser class
EngineResponses *engineResponses;
EngineRequests *engineRequests;
//..
EngineResponses *engineResponses;
@protocol PassParsedData
- (void)sendArray:(NSArray *)array;
@end
//..
id <PassParsedData> mydelegate;
//..
@property (strong) id <PassParsedData> mydelegate;
。。。试试看:)好的。我将根据您更新的代码重新执行此操作。为了方便起见,我复制了您的代码并进行了修改 ViewController.h
#import "EngineResponses.h" //delegates & protocols
interface SearchViewController : UITableViewController <PassParsedData> {
//delegates to parser class
EngineResponses *engineResponses;
//..
@protocol PassParsedData
- (void)sendArray:(NSArray *)array;
@end
//..
id <PassParsedData> mydelegate;
//..
@property (strong) id <PassParsedData> mydelegate;
#import "EngineResponses.h" //delegates & protocols
interface SearchViewController : UITableViewController <PassParsedData> {
//delegates to parser class
EngineResponses *engineResponses;
EngineRequests *engineRequests;
//..
EngineResponses *engineResponses;
@protocol PassParsedData
- (void)sendArray:(NSArray *)array;
@end
//..
id <PassParsedData> mydelegate;
//..
@property (strong) id <PassParsedData> mydelegate;
说明:EngineRequests现在是一个实例变量,不应在本地重新定义。
您可以在本地定义一个相同名称的变量,该变量将隐藏实例变量。我想
在这种情况下,您会得到一个编译器警告,但这会起作用,并且很可能会让您感到困惑。
同样,如果您一次使用多个请求,那么此解决方案将不起作用
引擎请求.h
#import "EngineResponses.h" //delegates & protocols
interface SearchViewController : UITableViewController <PassParsedData> {
//delegates to parser class
EngineResponses *engineResponses;
//..
@protocol PassParsedData
- (void)sendArray:(NSArray *)array;
@end
//..
id <PassParsedData> mydelegate;
//..
@property (strong) id <PassParsedData> mydelegate;
#import "EngineResponses.h" //delegates & protocols
interface SearchViewController : UITableViewController <PassParsedData> {
//delegates to parser class
EngineResponses *engineResponses;
EngineRequests *engineRequests;
//..
EngineResponses *engineResponses;
@protocol PassParsedData
- (void)sendArray:(NSArray *)array;
@end
//..
id <PassParsedData> mydelegate;
//..
@property (strong) id <PassParsedData> mydelegate;
EngineRequests.m
#import "EngineResponses.h"
//this is where I set up the delegate/protocol for the parser class
- (void)viewDidLoad
{
[super viewDidLoad];
//..
engineResponses = [[EngineResponses alloc] init];
[engineResponses setMydelegate:self];
//..
}
//this is where i set up and call the connection class
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
//..
if(indexPath.section == 0){
//..
if (indexPath.row == 0){
EngineRequests *engineRequests = [[EngineRequests alloc] init];
[engineRequests initalizePacketVariables:0 startCode:@"myReg" activationCode:@"myAct" methodName:@"GetStuff"];
//..
}
#pragma - Reciver methods
- (void)sendArray:(NSArray *)array
{
ICMfgFilterArray = array;
[self.tableView reloadData];
}
//connection delegates etc..
//then I pass the data from the connection delegates over to the parser class
- (void)connectionDidFinishLoading:(NSURLConnection *)connection
{
EngineResponses *engineResponses = [[EngineResponses alloc] init];
[engineResponses ReciveResponse:receivedData];
}
- (void)parserDidEndDocument:(NSXMLParser *)parser
{
//..
[[self mydelegate]sendArray:filteredArray];
}
#import "EngineResponses.h"
//this is where I set up the delegate/protocol for the parser class
- (void)viewDidLoad
{
[super viewDidLoad];
//..
engineResponses = [[EngineResponses alloc] init];
[engineResponses setMydelegate:self];
engineRequests = [[EngineRequests alloc] init]; // Use instance variable instead of local variable
[engineRequests setEnineResponses:engineResponses];
//..
}
//this is where i set up and call the connection class
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
//..
if(indexPath.section == 0){
//..
if (indexPath.row == 0){
[engineRequests initalizePacketVariables:0 startCode:@"myReg" activationCode:@"myAct" methodName:@"GetStuff"];
//..
}
#pragma - Reciver methods
- (void)sendArray:(NSArray *)array
{
ICMfgFilterArray = array;
[self.tableView reloadData];
}
@synthesize engineResponses;
//connection delegates etc..
//then I pass the data from the connection delegates over to the parser class
- (void)connectionDidFinishLoading:(NSURLConnection *)connection
{
//EngineResponses *engineResponses = [[EngineResponses alloc] init]; //This Object has already been created!
[engineResponses ReciveResponse:receivedData];
}
- (void)parserDidEndDocument:(NSXMLParser *)parser
{
//..
[[self mydelegate]sendArray:filteredArray];
}
说明:这里对EngineResponses的引用现在也是一个实例变量,而不是本地定义的变量。对象不会是新创建的,但它引用了在视图控制器中创建的对象。这是EngineResponse“知道”其视图控制器对象的一个,因此可以传回解析的数据
引擎响应。h
#import "EngineResponses.h" //delegates & protocols
interface SearchViewController : UITableViewController <PassParsedData> {
//delegates to parser class
EngineResponses *engineResponses;
//..
@protocol PassParsedData
- (void)sendArray:(NSArray *)array;
@end
//..
id <PassParsedData> mydelegate;
//..
@property (strong) id <PassParsedData> mydelegate;
#import "EngineResponses.h" //delegates & protocols
interface SearchViewController : UITableViewController <PassParsedData> {
//delegates to parser class
EngineResponses *engineResponses;
EngineRequests *engineRequests;
//..
EngineResponses *engineResponses;
@protocol PassParsedData
- (void)sendArray:(NSArray *)array;
@end
//..
id <PassParsedData> mydelegate;
//..
@property (strong) id <PassParsedData> mydelegate;
。。。试试看:)始终检查零对象。向nil对象发送消息将不起任何作用,您的应用程序将继续。我敢打赌这就是问题所在,因为您在各地都进行了本地分配。为什么不将receivedata方法改为静态方法呢?因为在某些计算和解析过程中,似乎不需要这些类。那么零对象将不是一个因素。始终检查零对象。向nil对象发送消息将不起任何作用,您的应用程序将继续。我敢打赌这就是问题所在,因为您在各地都进行了本地分配。为什么不将receivedata方法改为静态方法呢?因为在某些计算和解析过程中,似乎不需要这些类。那么零对象就不是一个因素。你的代码的编辑版本比散文描述更容易诊断。嗯,你在做类似于
[myParser setDelegate:myViewController]的事情吗代码>?此外,我还需要查看您的代码以提出更好的解决方案。好的,我已经用我的代码进行了更新。。对不起,花了这么长时间,只是确保我把所有东西都准备好了。。所以我认为错误在于我在两个地方分配解析器对象。。。但是我不确定这是否正确,或者如何解决它。那么,你的“文件名”和你的类名匹配吗?或者ParserClass是你的引擎响应?似乎是这样。如果是这样的话,那么你会无缘无故地分配两次。在ConnectiondFinish中,您创建了一个新的。现在它的mydelegate最初设置为nil(我猜)。因此,当您向mydelegate发送sendArray消息时,它是nil,然后向nil对象发送消息。这既不会导致编译器错误,也不会导致运行时错误,但肯定不会执行sendArray方法。确保您的连接类