首页 > 解决方案 > 将 Swift 4 字符串传递给 Obj-C++ 时遇到问题 - [_SwiftValue dataUsingEncoding:]:无法识别的选择器已发送到实例

问题描述

我有一些像这样的 Objective-C++ 代码:

// header

@interface MyObjcClass

- (void) myMethod: (NSString *) text;

@end


// implementation

@implementation MyObjcClass

- (void) myMethod: (NSString *) text
{
    someInternalObject->useWstring(nsStringToWstring(text))
}

std::wstring nsStringToWstring(const NSString * text)
{
    NSData * data = [text dataUsingEncoding: NSUTF32LittleEndianStringEncoding];

    // and then some other stuff irrelevant to this question

    return std::wstring(pointerToNewString, pointerToNewString + stringLength);
}

@end

到目前为止直截了当;对我来说似乎很好。从 Objective-C 和 Objective-C++ 代码调用时效果很好!然而,当斯威夫特参与其中时......

func mySwiftFunc(text: String) {
    myObjcClassInstance.myMethod(text)
}

这似乎也很简单。编译器的翻译层自动将 SwiftString与 Objective-C++ 的NSString *. 不幸的是,这是错误的......它似乎将它与名为_SwiftValue. 然后它被传入,我尝试调用dataUsingEncoding:它,但显然_SwiftValue没有这样的选择器,所以我得到了这个崩溃:

*** Terminating app due to uncaught exception 'NSInvalidArgumentException', reason: '-[_SwiftValue dataUsingEncoding:]: unrecognized selector sent to instance 0x7f9ca7d63ee0'

我不知道如何解决这个问题。我不能NSString在 Swift 中使用,只是将其传递下去,因为编译器要求我传递一个 Swift String

有没有办法解决这个问题?

这些解决方案中的任何一个都可以:


环境

标签: swiftnsstringselectorobjective-c++

解决方案


我会尝试

func mySwiftFunc(text: String) {
     myObjcClassInstance.perform(#selector(NSSelectorFromString("myMethod:"), with: text as NSString)
}

如果这不起作用,请尝试:

func mySwiftFunc(text: String) {
    let selector : Selector = NSSelectorFromString("myMethod:")
    let methodIMP : IMP! = myObjcClassInstance.method(for: selector)
    unsafeBitCast(methodIMP,to:(@convention(c)(Any?,Selector,NSString)->Void).self)(myObjcClassInstance,selector,text as NSString)
}

可能没有选择器名称"myMethod:"字符串依赖,但我跳过了铸造体操,因为它不是问题的本质。


推荐阅读