Ios 如何在目标c文件中访问swift公共功能?
我使用下面的public方法将API数据类型转换为IntIos 如何在目标c文件中访问swift公共功能?,ios,objective-c,swift,Ios,Objective C,Swift,我使用下面的public方法将API数据类型转换为Int public func convertToInt( value : Any) -> Int{ if let v = value as? String { if let myNumber = NSNumberFormatter().numberFromString(v) { return myNumber.integerValue } else {
public func convertToInt( value : Any) -> Int{
if let v = value as? String {
if let myNumber = NSNumberFormatter().numberFromString(v) {
return myNumber.integerValue
} else {
print ("Cannot convert to Int...")
}
} else if let v = value as? Int {
return v
} else if let v = value as? NSNumber {
return v.integerValue
}
return 0
}
我在我的项目中同时使用swift和objective c文件。我想访问这个函数到目标c文件也。如果有人知道解决方案,请帮助我。将您的项目设置为同时使用swift和objective c。然后,您需要以与导入Objective C类类似的方式导入Swift类,并以与在Objective C类中使用相同的方式使用它。问题在于,协议
任何
都不能在Objective-C中表示
因此,一种可能的解决方案是将函数封装在助手类中,并对值参数使用AnyObject
,因为Int
和String
可以分别自由桥接到NSNumber
和NSString
,因此,当基础被导入时,可以将其视为对象。
@objc final class HelperFunctions : NSObject {
static func convertToInt(value : AnyObject) -> Int {
if let v = value as? String {
if let myNumber = NSNumberFormatter().numberFromString(v) {
return myNumber.integerValue
} else {
print ("Cannot convert to Int...")
}
} else if let v = value as? Int {
print("int")
return v
}
// note that this check is completely redundant as NSNumber is freely bridgable
// to Int – therefore the 'as? Int' check will always get triggered instead
else if let v = value as? NSNumber {
print("nsnum")
return v.integerValue
}
return 0
}
}
尽管如此,这真的不是很快的代码NSNumber
可桥接到Int
,因此您可以直接转换它:
let n = NSNumber(integer: 5)
let i = n as Int // 5
并且Int
已经有了一个可以接受字符串的初始化器:
let i = Int("55") // Optional(55)
所以,我真的看不出这个函数解决了什么Swift问题。虽然我确实看到了Objective-C正在解决的问题,出于这个原因,我只想在Objective-C文件中将此函数作为C函数实现
extern NSInteger convertToInt(id _Nonnull value);
如果您真的愿意,您可以随时将其导入Swift,然后它将作为一个全局函数提供。但我建议您不要将其导入Swift,而是找到一个更快速的解决方案
例如,我建议您使用协议和扩展在Swift中实现这一点。您可以定义一个IntRepresentable
协议来表示可以转换为Int
的类型。这样做的好处是,您可以明确地将类型转换为Int
,而不是让它成为便利函数的实现细节
protocol IntRepresentable {
func _asInt() -> Int?
}
现在,您可以扩展字典中可能包含的类型,并使它们符合IntRepresentable
extension NSString : IntRepresentable {
func _asInt() -> Int? {return Int(self as String)}
}
extension NSNumber : IntRepresentable {
func _asInt() -> Int? {return self.integerValue}
}
// not really necessary, as your dict will be [Whatever:AnyObject],
// so the NSString extension will be used – here for completeness
extension String : IntRepresentable {
func _asInt() -> Int? {return Int(self)}
}
extension Int : IntRepresentable {
func _asInt() -> Int? {return self}
init?(representable:IntRepresentable) {
guard let i = representable._asInt() else {return nil}
self = i
}
}
现在,您可以通过执行以下操作将词典从[whater:AnyObject]
转换为[whater:Int]
:
let inputDict = ["foo":"5", "bar":6, "baz":NSNumber(int:5)]
var outputDict = [String:Int]()
for (key, value) in inputDict {
if let value = value as? IntRepresentable {
outputDict[key] = Int(representable: value)
}
}
print(outputDict) // ["baz": 5, "foo": 5, "bar": 6]
如果这让你感觉更好,你可以把它放在一个方便的函数中,尽管我仍然反对全局函数。为了避免污染全局命名空间,可以使用无大小写枚举:
enum DictionaryConversion {
static func toIntValues<Key>(dict:[Key:NSObject]) -> [Key:Int] {
var outputDict = [Key:Int]()
for (key, value) in dict {
if let value = value as? IntRepresentable {
outputDict[key] = Int(representable: value)
}
}
return outputDict
}
}
我已经在我的项目中设置了。此公共函数不属于类。我们可以在任何地方调用它,而无需使用类名,就像“let value=convertToInt(“888”)”。我不知道如何在objective c文件中调用这个方法。不,我想你不能。而是创建一个Helper类,并将此公共函数作为该Helper类的类函数。谢谢。我在API调用中使用这个函数。我们不需要检查数据类型。我们可以简单地从字典中传递值。如果为零或不可转换,则返回0。这就是为什么我要用这个。我可以简单地调用“let value=covertToInt(dictionary[“key”])”。否则,我需要为每个变量和数据类型检查“if let value=dictionary[“key”]作为数据类型{}”。有人知道它是否会在Swift 3中更改吗?@karthikjin我已经更新了我的帖子,通过将字典本身转换为[where:Int]
来实现这一点。尽管在当前系统中,如果int值实际为0,会发生什么情况?您现在肯定要将其视为失败的转换?TQ用于您的解决方案@originaluser2。您的解决方案正在帮助我解决其他一些情况。我的默认值是0。这就是我一直将值返回为“0”的原因。@karthikjin很乐意帮助:)请确保它是否解决了您的问题。
enum DictionaryConversion {
static func toIntValues<Key>(dict:[Key:NSObject]) -> [Key:Int] {
var outputDict = [Key:Int]()
for (key, value) in dict {
if let value = value as? IntRepresentable {
outputDict[key] = Int(representable: value)
}
}
return outputDict
}
}
extension Dictionary {
func convertValuesToInt() -> [Key:Int] {
var outputDict = [Key:Int]()
for (key, value) in self {
if let value = value as? IntRepresentable {
outputDict[key] = Int(representable: value)
}
}
return outputDict
}
}
let outputDict = DictionaryConversion.toIntValues(inputDict)
let outputDict = inputDict.convertValuesToInt()