Objective c NSNotificationCenter选择器赢得';我不能处理它的通知

Objective c NSNotificationCenter选择器赢得';我不能处理它的通知,objective-c,cocoa,notifications,nsnotifications,Objective C,Cocoa,Notifications,Nsnotifications,我正在从事一个Cocoa项目,其中包含一些C(我知道,objc包含C…),我试图理解NSNotificationCenters。情况如下: 我将一个结构声明为typedef struct{/*code here*/}structName 在我的-(id)init方法中,我有 [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(selName:) name:@"notName" object:nil];

我正在从事一个Cocoa项目,其中包含一些C(我知道,objc包含C…),我试图理解
NSNotificationCenter
s。情况如下:

我将一个结构声明为
typedef struct{/*code here*/}structName

在我的
-(id)init
方法中,我有

[[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(selName:) name:@"notName" object:nil];
我有一个回调函数:

int callback(/*args*/) {
    structName *f = ...
    NSAutoreleasePool *autoreleasepool = [[NSAutoreleasePool alloc] init];
    [[NSNotificationCenter defaultCenter] postNotificationName:@"notName" object:[[NSValue valueWithPointer:f] retain]];
    [autoreleasepool release];
}
然后对于我的选择器:

- (void)selName:(NSNotification *)note
{
    NSLog(@"here");
    NSLog(@"note is %@", note);
}
现在,如果我注释掉第二个
NSLog
,一切似乎都正常(即“此处”已打印)。但是如果我把它留在里面,
NSNotification
似乎没有任何作用。但这似乎违背了
NSNotification
的对象、用户信息等的目的

我做错了什么?如何修复它,以便能够访问我的
structName f

@内森 好吧,现在我有了

NSDictionary *dict = [NSDictionary dictionaryWithObject:[NSValue valueWithPointer:f] forKey:@"fkey"];//f, not &f. I had a typo in the OP which I fixed.
[[NSNotificationCenter defaultCenter] postNotificationName:@"notName" object:nil userInfo:[dict retain]];
……但问题依然存在。这有可能和我修正的打字错误有关吗

编辑:

即使将上面的两行更改为

[[NSNotificationCenter defaultCenter] postNotificationName:@"notName" object:nil userInfo:[NSDictionary dictionaryWithObject:[NSData dataWithBytes:f length:sizeof(structName)] forKey:@"fkey"]];

NSValue
需要指向结构的指针,而不是结构本身:

[NSValue valueWithPointer:&f
]

您应该使用not

object参数是发送通知的对象。通常,对于发布通知的对象来说,这是self,但由于您是从C函数调用它,因此它应该是nil

userInfo参数是一个
NSDictionary
,因此将
NSValue
添加到一个dictionary并发送它

然后用selName:method从中获取dict并从中提取您的信息

注意:在不应该保留的情况下,保留
NSValue
会造成泄漏

编辑:

结构存在多长时间
NSValue
不会复制指针的内容,因此可能它正在被释放?尝试改用
NSData

还要确保检查控制台是否存在运行时错误(在Xcode:
Run>console


您不需要保留dict。您可能需要(重新)阅读文档

你有什么不同吗?

你说如果你把第二个
NSLog
注释掉就行了。第二个
NSLog
似乎不正确:

- (void)selName:(NSNotification *)note
{
    NSLog(@"here");
    NSLog(@"note is %@", note);   
}
%@
格式用于打印
NSString
,但“note”不是
NSString
,而是一个对象。NSNotification有一个name属性,返回一个
NSString
。尝试将第二个
NSLog
更改为:

NSLog(@"note is %@", [note name]);

相反,您可以使用以下选项:

- (void)selName:(NSNotification *)note
{
    NSLog(@"here");
    NSLog(@"note is %@", [note userInfo]);
}

好的,现在我有了NSDictionary*dict=[NSDictionary Dictionary WithObject:[NSValue valueWithPointer:f]forKey:@“fkey”]//f、 诺特餐饮公司。我修正了OP中的一个拼写错误。[[NSNotificationCenter defaultCenter]postNotificationName:@“notName”对象:无用户信息:[dict retain]]。。。但问题依然存在。有没有可能跟我修正的打字错误有关?哇。我第一次在这里发帖。。。我编辑了OP,因此您可以实际查看其格式。已尝试[[NSNotificationCenter defaultCenter]postNotificationName:@“notName”对象:无用户信息:[NSDictionary Dictionary Dictionary WithObject:[NSData dataWithBytes:f length:sizeof(structName)]forKey:@“fkey”];还是不走运。谢谢你一直以来的帮助。我正在做的一件非常愚蠢的事情就是一行NSLog破坏了一切,甚至不允许打印“here”。尝试创建一个新项目,并测试发送通知所需的最低限度(没有用户信息,只有名称)。然后一次添加一点(比如在字典中发送NSString)。看看你是否能让它工作,然后,如果可以的话,试着找出你的主要项目有什么不同。内森:如果他想让dict生活在自动释放池之外,他确实需要保留dict。NSNotification文档没有说明它是否保留userInfo。如果我将代码保持在“工作”状态,并将structName声明更改为与您相同的状态(即struct structName{…};),那么我的代码将不再工作。这是一个区别。另外,我在my.m中声明struct和C函数,而不是在my.h中声明。可以刚刚将这些声明移动到my.h,但仍然必须使用
typedef
。还是没有乐趣。让我试着说一些更有用的话。线程/死锁问题会导致我的问题吗?语法问题,如是否使用“struct structName”或typedef it并使用该名称是不相关的。无论您是在头中声明内容还是在实现中声明内容;这只会影响这些符号对其他文件的可见性,而不会影响它们在正在运行的程序中的行为。因此,即使是后面的NSLog也不会造成问题。我认为这更可能是随机的。尝试将其放回原处并反复运行,您会发现您的通知处理程序有时确实会被调用。然后,取出语句并反复运行。你应该会发现同样的事情。至于线程导致死锁:如果你有线程,它可能会。使用鲨鱼或仪器查看发生了什么。此外,每个线程都有运行循环,因此请检查以确保始终在添加观察者并在同一(以及正确)线程上发布通知。
%@
说明
发送到对象并打印该字符串。因此,它适用于所有NSObject和某些CFType。来源:(它确实说它在CFTypes上使用了
CFCopyDescription
,这应该适用于所有这样的对象,但我已经让它返回了一些CFTypes的空字符串。下次遇到这个问题时,我应该提交一个bug。)感谢Peter的更正和链接。我不知道%@可以与NSString以外的任何东西一起使用。所以他的代码应该是有效的。