Objective-C在swift类上请求alloc

时间:2014-06-04 13:53:39

标签: objective-c swift alloc

一些小步骤开始围绕Swift缠头。我基本上移植了一个旧类,它只是找到一个名称的匹配图标并返回相应的UIImage。事情的Swift部分似乎已经启动并且看起来(几乎)像这样:

@objc class ImageHandler{

    func iconForData(data: MyData) -> UIImage{
        let imagesAndNames = [
            "1": "tree.png",
            "2": "car.png",
            "3": "house.png",
            "7": "boat.png",
        ]

        var imageName: String? = imagesAndNames[data.imageName]
        if !imageName{
            imageName = "placeholder.png"
        }
        let icon = UIImage(named: imageName)
        return icon
    }
}

上面没有任何警告。然而,我的旧Objective-C类要求在swift类上使用alloc方法。

ImageHandler *imageHandler = [ImageHandler alloc] init];

返回错误“没有选择器'alloc'的已知类方法,这是真的,我猜,但是如何逃避这个?我基于我的swift类的NSObject来避免此?

5 个答案:

答案 0 :(得分:47)

您将ImageHandler类声明为根类。它本身没有alloc方法。您需要继承NSObject

@objc class ImageHandler : NSObject {

    ...

}

引自this ADF thread

答案 1 :(得分:24)

这里只是想评论一下,如果你不想继承NSObject或任何其他ObjC对象,你可以声明一个类级初始化器:

@objc class ImageHandler{

    class func newInstance() -> ImageHandler {
        return ImageHandler()
    }

    func iconForData(data: MyData) -> UIImage{
        let imagesAndNames = [
            "1": "tree.png",
            "2": "car.png",
            "3": "house.png",
            "7": "boat.png",
        ]

        var imageName: String? = imagesAndNames[data.imageName]
        if !imageName{
            imageName = "placeholder.png"
        }
        let icon = UIImage(named: imageName)
        return icon
    }
}

然后在ObjC

ImageHandler * imageHandler = [ImageHandler newInstance];

这样,除非你想要,否则你不必依赖于ObjC类继承。

答案 2 :(得分:3)

这个答案是你想继续使用纯swift对象,并且不想继承NSObject。如果您不关心使用纯粹的快速物体,请使用上面的akashivskyy答案。

我遇到了同样的问题。我接受了Logan的回答并对其进行了修改,以便Objective-C调用者不必改变行为。如果你像我一样,并构建一个可以被Objective-C或Swift项目使用的框架,这一点尤为重要。

@objc public class TestClass {

    public init(){}

    public class func alloc() -> TestClass {return TestClass()}

}

Objective-C实现变得熟悉。

TestClass *testClass = [[TestClass alloc] init];

Swift实现也保持不变。

let testClass = TestClass()

编辑: 此外,我继续将其实现为一个可以被其他纯swift对象子类化的类。

@objc public class ObjectiveCCompatibleObject {

    required public init(){}

    public class func alloc() -> Self {return self()}
}

答案 3 :(得分:1)

如果我们想要在Objective C中导入swift文件,那么

import“productname-Swift.h”或使用尖括号<>

目标C文件中的

。然后可以在Objective C中访问特定导入的swift类的alloc,init。

答案 4 :(得分:-1)

你可以这样做:

ImageHandler *imageHandler =
    [[NSClassFromString(@"YourProjectName.ImageHandler") alloc] init];

(或者,如果您在Swift中完成了@objc(ImageHandler) class ImageHandler,那么您会[[NSClassFromString(@"ImageHandler") alloc] init]


或者,您可以在Objective-C文件的顶部声明(但不实现)包含alloc方法的虚拟类别:

@interface ImageHandler (Dummy)
+ (instancetype)alloc;
@end

然后您可以直接在代码中使用它:

ImageHandler *imageHandler = [[ImageHandler alloc] init];