在Objective C中,您可以使用以下命令记录正在调用的方法:
NSLog(@"%s", __PRETTY_FUNCTION__)
Run Code Online (Sandbox Code Playgroud)
通常,这是从日志记录宏中使用的.
虽然Swift不支持宏(我认为),但我仍然希望使用包含被调用函数名称的通用日志语句.在Swift中可以吗?
更新: 我现在使用此全局函数进行日志记录,可在此处找到:https: //github.com/evermeer/Stuff#print 您可以使用以下命令安装:
pod 'Stuff/Print'
Run Code Online (Sandbox Code Playgroud)
这是代码:
public class Stuff {
public enum logLevel: Int {
case info = 1
case debug = 2
case warn = 3
case error = 4
case fatal = 5
case none = 6
public func description() -> String {
switch self {
case .info:
return "?"
case .debug:
return "??"
case .warn:
return "??"
case .error:
return ""
case .fatal:
return ""
case .none:
return …
Run Code Online (Sandbox Code Playgroud) 在Swift中,它不可能使用 .setValue(..., forKey: ...)
Int
?enum
类型的属性[MyObject?]
这有一个解决方法,即通过覆盖对象本身中的setValue forUndefinedKey方法.
因为我正在编写一个基于反射的通用对象映射器.请参阅EVReflection我希望尽可能地减少这种手动映射.
还有其他方法可以自动设置这些属性吗?
解决方法:可以在我的库中的单元测试发现这里 这是代码:
class WorkaroundsTests: XCTestCase {
func testWorkarounds() {
let json:String = "{\"nullableType\": 1,\"status\": 0, \"list\": [ {\"nullableType\": 2}, {\"nullableType\": 3}] }"
let status = Testobject(json: json)
XCTAssertTrue(status.nullableType == 1, "the nullableType should be 1")
XCTAssertTrue(status.status == .NotOK, "the status should be NotOK")
XCTAssertTrue(status.list.count == 2, "the list should have 2 items")
if status.list.count == 2 {
XCTAssertTrue(status.list[0]?.nullableType == 2, "the …
Run Code Online (Sandbox Code Playgroud) 在我的聊天应用程序中,我使用JSQMessagesViewController来呈现对话.该应用程序还有我要搜索的公共消息.我现在尝试使用JSQMessagesViewController显示它们.为此我想隐藏inputToolbar(可以工作)并添加一个搜索栏.
如何使搜索栏可见?当您查看属性topContentAdditionalInset时,它看起来应该是可能的.这是我尝试的代码:
override func viewDidLoad() {
super.viewDidLoad()
self.inputToolbar.removeFromSuperview()
self.searchBar.removeFromSuperview()
self.topContentAdditionalInset = 44
self.searchBar.frame = CGRect(x: 0, y: 25, width: 320, height: 44)
// Attempt 1
// self.collectionView.addSubview(self.searchBar)
// Attempt 2
// self.view.addSubview(self.searchBar)
// Attempt 3
// self.navigationController?.navigationBar.addSubview(self.searchBar)
// Attempt 4
// self.inputToolbar.addSubview(self.searchBar)
// Attempt 5
self.collectionView.superview!.addSubview(self.searchBar)
}
Run Code Online (Sandbox Code Playgroud)
更新:
以下代码似乎可以正常工作.它的问题是: - 它是collectionView的一个子项,因此将滚动显示内容.将其添加到.superview不起作用. - 当搜索栏获得焦点时,它向下滚动44个像素.
var keepRef:JSQMessagesInputToolbar!
var searchBar:UISearchBar!
override func viewDidAppear(animated: Bool) {
super.viewDidAppear(animated)
if self.inputToolbar.superview != nil {
keepRef = self.inputToolbar
self.inputToolbar.removeFromSuperview()
}
self.topContentAdditionalInset = 44
if searchBar …
Run Code Online (Sandbox Code Playgroud) 可以smb解释是什么问题,我应该如何修改我的代码?
我需要过滤CKRecord
从中返回的s CloudKit
.
override func tableView(tableView: UITableView, moveRowAtIndexPath sourceIndexPath: NSIndexPath, toIndexPath destinationIndexPath: NSIndexPath) {
let defaultContainer = CKContainer.defaultContainer()
let publicDatabase = defaultContainer.publicCloudDatabase
let myfunc2 = myfunc(names, { (records: [CKRecord], error: NSError) in
if error == nil {
let records2 = records.filter($0.value > sourceIndexPath.row && $0.value < destinationIndexPath.row)
let mro = CKModifyRecordsOperation(recordsToSave: [], recordIDsToDelete: [])
} else {
}
})
Run Code Online (Sandbox Code Playgroud)
2015年8月28日更新: 这将在Swift 2中解决
2015年10月23日更新:使用Swift 2泛型,您仍然无法获得rawValue.你可以得到相关的价值.
原始问题:
我有一些用swift编写的通用反射代码.在该代码中,我无法获取基于枚举的属性的值.问题归结为我无法执行.rawValue
属性类型的属性Any
.Swift反射代码将返回枚举值作为类型Any
.那么我怎样才能从Any到AnyObject,它是枚举的rawValue.
到目前为止,我发现的唯一解决方法是使用协议扩展所有枚举.您可以在下面看到使用此变通方法的单元测试.
有没有办法解决这个问题,而无需在原始枚举中添加代码?
对于我的反射代码,我需要getRawValue
方法签名保持不变.
class WorkaroundsTests: XCTestCase {
func testEnumToRaw() {
let test1 = getRawValue(MyEnumOne.OK)
XCTAssertTrue(test1 == "OK", "Could nog get the rawvalue using a generic function")
let test2 = getRawValue(MyEnumTwo.OK)
XCTAssertTrue(test2 == "1", "Could nog get the rawvalue using a generic function")
let test3 = getRawValue(MyEnumThree.OK)
XCTAssertTrue(test3 == "1", "Could nog get the rawvalue using a generic function")
} …
Run Code Online (Sandbox Code Playgroud) 我正在尝试制作通用的NSCoding实现,并且由于更新版本的应用程序,当对象的类型在平均时间内发生变化时会出现解码问题.
我从Swift调用validateValue方法时遇到问题.功能签名是:
func validateValue(_ ioValue: AutoreleasingUnsafeMutablePointer<AnyObject?>, forKey key: String, error outError: NSErrorPointer) -> Bool
Run Code Online (Sandbox Code Playgroud)
作为参考,Apple文档可以在这里找到:NSCoding validateValue
我想要创建的代码是:
public class func decodeObjectWithCoder(theObject:NSObject, aDecoder: NSCoder) {
for (key, value) in toDictionary(theObject) {
if aDecoder.containsValueForKey(key) {
let newValue: AnyObject? = aDecoder.decodeObjectForKey(key)
NSLog("set key \(key) with value \(newValue)")
var error:NSError?
var y:Bool = theObject.validateValue(newValue, forKey: key, error: &error)
if y {
theObject.setValue(newValue, forKey: key)
}
}
}
}
Run Code Online (Sandbox Code Playgroud)
我无法正确调用.validateValue.我不断收到编译错误.我该怎么称呼它.toDictionary函数可以在以下位置找到:EVReflection
更新:我刚刚发现这段代码编译:
var ioValue: AutoreleasingUnsafeMutablePointer<AnyObject?> = nil
var y:Bool = theObject.validateValue(ioValue, forKey: key, …
Run Code Online (Sandbox Code Playgroud) 在我的Swift库EVCloudKitDao中,我做了很多反思.因此,我已将我的数据对象的基类设置为NSObject.现在升级到Xcode 6.3后,我得到了2个函数的错误,用于获取哈希和对象的描述.描述函数很不错,但我确实需要哈希来使我的对象使用Set.
这是我的代码
public class EVCloudKitDataObject : NSObject, NSCoding, Printable, Hashable, Equatable {
public func hash() -> Int {
return self.hashValue
}
public func description() -> String {
return EVReflection.description(self)
}
}
Run Code Online (Sandbox Code Playgroud)
我得到的错误是:
/Users/evermeer/Desktop/dev/GitHub/EVCloudKitDao/AppMessage/AppMessage/CloudKit/EVCloudKitDataObject.swift:106:17:使用Objective-C选择器'hash'的方法'hash()'与来自超类的'hash'的getter冲突'NSObject'具有相同的Objective-C选择器
/Users/evermeer/Desktop/dev/GitHub/EVCloudKitDao/AppMessage/AppMessage/CloudKit/EVCloudKitDataObject.swift:86:17:使用Objective-C选择器'description'的方法'description()'与来自超类的'description'的getter冲突'NSObject'具有相同的Objective-C选择器
有谁知道我怎么能解决这个问题?你不能使用覆盖.
我正在尝试创建一个Codable扩展,它能够仅使用json字符串初始化Decodable(Swift 4)对象.那应该是什么工作:
struct MyObject: Decodable {
var title: String?
}
let myObject = MyObject(json: "{\"title\":\"The title\"}")
Run Code Online (Sandbox Code Playgroud)
我认为这意味着我应该创建一个使用Decoder调用self.init的init.这是我提出的代码:
public init?(json: String) throws {
guard let decoder: Decoder = GetDecoder.decode(json: json)?.decoder else { return }
try self.init(from: decoder) // Who what should we do to get it so that we can call this?
}
Run Code Online (Sandbox Code Playgroud)
该代码能够获取解码器,但是在调用init时出现编译器错误.我得到的错误是:
在self.init电话之前使用'self'
这是否意味着无法在Decodable协议中添加init?
更新:
从@appzYourLive调试下面的解决方案后,我发现我与init(json:
Decodable和Array上的初始化程序有冲突.我刚刚向GitHub发布了新版本的扩展.我还添加了解决方案作为这个问题的新答案.
我正在尝试创建CloudKit文本搜索查询.什么工作是查询以搜索文本开头的记录,如下所示:
NSPredicate(format: "Text BEGINSWITH %@", searchText)!
Run Code Online (Sandbox Code Playgroud)
令牌搜索也有效(查询其中一个输入的单词是否在记录中的某个位置),如下所示:
NSPredicate(format: "allTokens TOKENMATCHES[cdl] %@", searchText)!
Run Code Online (Sandbox Code Playgroud)
你可以在EVCloudKitDao的演示应用程序中看到这些查询(参见截图)
但现在我想结合这两个查询,以便结果感觉更完整.我尝试使用此查询:
NSPredicate(format: "Text BEGINSWITH %@ OR allTokens TOKENMATCHES[cdl] %@", searchText, searchText)!
Run Code Online (Sandbox Code Playgroud)
但是我会得到这个CloudKit错误:
因未捕获的异常'CKException'而终止应用程序,原因:'意外表达:文本BEGINSWITH"Y"或allTokens TOKENMATCHES [cdl]"Y"'
除此之外,我还尝试了这样的NSCompoundPredicate:
var p1 = NSPredicate(format: "allTokens TOKENMATCHES[cdl] %@", searchText)!
var p2 = NSPredicate(format: "Text BEGINSWITH %@", searchText)!
var p = NSCompoundPredicate(type: NSCompoundPredicateType.OrPredicateType, subpredicates: [p1, p2])
Run Code Online (Sandbox Code Playgroud)
但是那个给出了同样的错误:
由于未捕获的异常'CKException'而终止应用程序,原因:'意外的表达式:allTokens TOKENMATCHES [cdl]"y"或文本BEGINSWITH"y"'
奇怪的是,它在使用AndPredicateType而不是OrPredicateType时确实有效
有谁知道像这样的查询的替代解决方案?由于它是一个自动完成功能,执行2个查询并组合结果不是一个真正的选择.
在我的反射库EVReflection中,当类定义嵌套(类中的类)时,我遇到以下问题。下面是一个已解决的案例,可以在此处作为单元测试找到,库本身中需要更改代码的位置是此处
我需要为一个属性获取嵌套类的内部 Swift 字符串表示,该属性是该嵌套类的数组。
您可以在下面看到一个单元测试,其中我能够为作为其他对象的财产公司获取正确的类型。它会输出_TtCC22EVReflection_iOS_Tests13TestIssue114b10Company114
而不是Company114
当我对friends 属性尝试同样的操作时,我的目标是输出如下内容:Swift.Array<_TtCC22EVReflection_iOS_Tests13TestIssue114b7User114>
我需要做什么才能得到它?
正如您在测试中看到的,我对 valueType 值进行了各种分配。这些任务都不起作用。我只能得到 anArray<User114>
或 an Swift._EmptyArrayStorage
。
正如您在测试中还看到的那样,如果我设置断点并在输出窗口中执行 po 操作,我就可以获得正确的输出。那么什么代码会在我的代码中实现相同的功能呢?
class TestIssue114b: XCTestCase {
class User114: EVObject {
var company: Company114 = Company114()
var friends: [User114] = []
}
class Company114: EVObject {
var name: String = ""
var address: String?
}
func testIssueNestedObjects() {
let x = User114()
print("type 1 = \(NSStringFromClass(type(of: x.company)))") // output = …
Run Code Online (Sandbox Code Playgroud)