如何在Obj-C或Swift中访问私有实例变量?

时间:2018-02-21 14:48:42

标签: objective-c swift macos instance-variables access-modifiers

我试图在macOS上访问Swift中MKMapSnapshotter的私有实例变量_lodpiSnapshotCreator_hidpiSnapshotCreator

感谢课堂转储,我知道他们在那里(see here):

@interface MKMapSnapshotter : NSObject
{
    [...]
    VKMapSnapshotCreator *_lodpiSnapshotCreator;
    VKMapSnapshotCreator *_hidpiSnapshotCreator;
}

但无论我做什么,我都无法得到它们。

这是我检查是否可以访问它们的方式:

let snapshotter = MKMapSnapshotter(options: snapshotOptions)

let varNames = ["_lodpiSnapshotCreator", "_hidpiSnapshotCreator"]
for varName in varNames {
    if let testIVar = class_getInstanceVariable(MKMapSnapshotter.self, varName) {
        if let test = object_getIvar(snapshotter, testIVar) as? VKMapSnapshotCreator {
            print(test)
        } else {
            print("Got ivar, but \(varName) is still nil (getInstanceVariable)")
        }
    } else {
        print("\(varName) is nil (getInstanceVariable)")
    }
}

奇怪的是,class_getInstanceVariable并没有返回nil,但是object_getIvar却没有。

Got ivar, but _lodpiSnapshotCreator is still nil (getInstanceVariable)
Got ivar, but _hidpiSnapshotCreator is still nil (getInstanceVariable)

我的智慧在这里结束了。我通过Google找到的所有人都建议使用class_getInstanceVariable(我已经使用过)和键值编码(它根本不起作用)。

这一定是以前做过的。任何人都可以帮助我吗?

修改:到目前为止,我已尝试过这个:

@interface MKMapSnapshotter() {
    @public VKMapSnapshotCreator *_lodpiSnapshotCreator;
    @public VKMapSnapshotCreator *_hidpiSnapshotCreator;
}

@end

编译成功,但在尝试使用它时,Swift坚持要求成员_lodpiSnapshotCreator和_hidpiSnapshotCreator不存在。

1 个答案:

答案 0 :(得分:1)

由于我们没有或没有控制源代码,我们无法将变量更改为属性。试过这个适用于您的情况:

extension MKMapSnapshotter {
   func getPrivateVariable() -> String? {
       return value(forKey: "_lodpiSnapshotCreator") as? String
   }

   open override func value(forUndefinedKey key: String) -> Any? {
       if key == "_lodpiSnapshotCreator" {
           return nil
       }
       return super.value(forUndefinedKey: key)
   }
}

您可以找到有关此here的更多信息。

如果这不起作用,那么我认为没有办法从Swift访问Objective-C实例变量。只有Objective-C属性才会映射到Swift属性。

希望这会有所帮助!!