zoukankan      html  css  js  c++  java
  • (转)ios error:unrecognized selector sent to class

    转自:http://blog.itpub.net/12231606/viewspace-1081952/

    今天将app统计的.a静态库包含到一个app应用中,调试时报下面的错误:

    *** Terminating app due to uncaught exception 'NSInvalidArgumentException', reason: '+[NSDictionary dictionaryWithJSONString:error:]: unrecognized selector sent to class 0x235e7ec'

    unrecognized selector sent to class 0x235e7ec'

    *** First throw call stack:

    (

    0   CoreFoundation                      0x022195e4 __exceptionPreprocess + 180

    1   libobjc.A.dylib                     0x01f288b6 objc_exception_throw + 44

    2   CoreFoundation                      0x022b67a3 +[NSObject(NSObject) doesNotRecognizeSelector:] + 275

    3   CoreFoundation                      0x0220990b ___forwarding___ + 1019

    4   CoreFoundation                      0x022094ee _CF_forwarding_prep_0 + 14


    ...

    10  Foundation                          0x01b80597 -[NSThread main] + 76

    11  Foundation                          0x01b804f6 __NSThread__main__ + 1275

    12  libsystem_c.dylib                   0x02d625b7 _pthread_start + 344

    13  libsystem_c.dylib                   0x02d4cdce thread_start + 34

    )

    libc++abi.dylib: terminating with uncaught exception of type NSException


    纠结了好久,定位代码错误位置如下:

    1. NSString *retString = [network SendData:url data:requestDictionary];
    2.     NSError *error = nil;
    3.     NSDictionary *retDictionary = [ NSDictionary dictionaryWithJSONString:retString error:&error];
    4.     if(!error)
    5.     {
    6.         ret.flag = [[retDictionary objectForKey:@"flag" ] intValue];
    7.         ret.msg = [retDictionary objectForKey:@"msg"];
    8.     }
    9.     return ret;
    10.     }

    推断原因是:NSDictionary 是内嵌对象,但是dictionaryWithJSONString  另一个自定义对象的方法。为什么要用与NSDictionary  相同的名称,原因就是要返回NSDictionary 对象。

    自定义对象代码如下:

    1. @implementation NSDictionary (NSDictionary_JSONExtensions)
    2. + (id)dictionaryWithJSONData:(NSData *)inData error:(NSError **)outError
    3.     {
    4.     return([[CJSONDeserializer deserializer] deserialize:inData error:outError]);
    5.     }
    6. + (id)dictionaryWithJSONString:(NSString *)inJSON error:(NSError **)outError;
    7.     {
    8.     NSData *theData = [inJSON dataUsingEncoding:NSUTF8StringEncoding];
    9.     return([self dictionaryWithJSONData:theData error:outError]);
    10.     }
    11. @end

    所以,推断xcode没有正确解析代码,把dictionaryWithJSONString 方法错误认为是内嵌对象NSDictionary 的内部方法,但NSDictionary 没有这个方法,所以调试的时候,就找不到该方法的实现,报出错误信息:unrecognized selector sent to class 0x235e7ec'

    推断出问题的可能原因后,很有可能是工程的setting信息有问题。于是开始一个一个参数过,一开始以为是Search Paths的各种路径配置错误,后来验证不是。否则编译都应该过不去。
    于是,将范围定在Build Settings下的Linking的参数列表。马上有一个参数映入眼帘:Other Linker Flags,没有设置。通过google,查询相关说明:

    -all_load Loads all members of static archive libraries.

    -ObjC Loads all members of static archive libraries that implement an Objective-C class or category.

    -force_load (path_to_archive) Loads all members of the specified static archive library. Note: -all_load forces all members of all archives to be loaded. This option allows you to target a specific archive.

    翻译过来就是-all_load就是会加载静态库文件中的所有成员,-ObjC就是会加载静态库文件中实现一个类或者分类的所有成员,-force_load(包的路径)就是会加载指定路径的静态库文件中的所有成员。所以对于使用runtime时候的反射调用的方法应该使用这三个中的一个进行link,以保证所有的类都可以加载到内存中供程序动态调用

    到这里,基本就明白了,就是这个参数没有设置的原因。将Other Linker Flags=-ObjC,再重新调试,运行成功!!

  • 相关阅读:
    JSON解析之——Android
    Xml解析之——Java/Android/Python
    Design Pattern —— Singleton
    设计模式(10)--观察者模式
    设计模式(9)--建造者模式
    设计模式(8)--外观模式
    设计模式(7)--模板模式
    设计模式(6)--原型模式
    设计模式(5)--工厂模式
    设计模式(4)--代理模式
  • 原文地址:https://www.cnblogs.com/guoxiaoqian/p/4026388.html
Copyright © 2011-2022 走看看