如何检查变量是否为对象?

Pat*_*ick 3 objective-c

有没有办法在编译时执行以下操作?

int anInteger = 0;
__if_object(anInteger) {
    // send object some messages
}
__if_primitive(anInteger) {
    // do something else
}
Run Code Online (Sandbox Code Playgroud)

可以使用的虚拟情况是在下面定义__add_macro.

#define __add_macro(var, val) __something_goes_here__

int i = 1;
MyInteger* num = [[MyNumber alloc] initWithValue:1]

__add_macro(i, 4);
__add_macro(num, 4);

// both should now hold 5
Run Code Online (Sandbox Code Playgroud)

澄清/简

我想用一个宏没办法做到这一点.但是我仍然需要它来警告宏是否在错误的数据类型上使用.这两种类型是:objectnon-object).

要检查它是否是一个对象,这有效:

#define __warn_if_not_object(var) if(0){[(var) class];}
Run Code Online (Sandbox Code Playgroud)

我需要的:

#define _warn_if_object(var) if(0){__something_here__}
Run Code Online (Sandbox Code Playgroud)

同样,我需要在编译时发生这种情况.它可以抛出错误或警告.

谢谢

CRD*_*CRD 5

声明int变量时,实际上只能int在其中放置一个值.

虽然这是Objective-C,因此是C,所以你可以绕过几乎所有存在的类型保护机制,这是不应该建议的.事实上,并不能保证任何一个NSNumber参数甚至可以适用于一个int变量 - 而且如果你尝试并且绕过任何警告,那么一些比特只会被抛出使参考无效.

所以,不,虽然你可以告诉对象引用引用什么类,你通常不能告诉变量是否有一个整数值或一个对象引用 - 你甚至不应该尝试将这两个非常不同的东西放入相同的变量.

答案2

帕特里克,你的评论和澄清似乎暗示你不是试图通过询问(如何确定a中的值int是否是一个对象 - 上面回答,你没有)来做问题的开始,而是一些相当不同的东西. ..

我认为你所追求的是函数重载,而你似乎正在尝试使用宏,也许是内联函数.Clang支持函数重载,这里是程序片段,可以告诉你如何解决你的问题:

// Clang likes prototypes so let's give it some
// The following declares two overloaded inline functions:
NS_INLINE void __attribute__((overloadable)) byType(int x);
NS_INLINE void __attribute__((overloadable)) byType(NSNumber *x);

// now some simple definitions:
NS_INLINE void __attribute__((overloadable)) byType(int x)
{
   NSLog(@"int version called: %d", x);
}

NS_INLINE void __attribute__((overloadable)) byType(NSNumber *x)
{
   NSLog(@"NSNumber version called: %@", x);
}

// now call them, automatically selecting the right function
// based on the argument type
- (void)applicationDidFinishLaunching:(NSNotification *)aNotification
{
   int x = 5;
   NSNumber *y = [NSNumber numberWithInt:42];

   byType(x);
   byType(y);
}
Run Code Online (Sandbox Code Playgroud)

以上代码运行时输出:

int version called: 5
NSNumber version called: 42
Run Code Online (Sandbox Code Playgroud)

Clang 3编译上面代码内联两个调用,因此您获得与使用宏相同的代码.