我在输入时搜索用户。但是最后它返回了每个用户。我不知道为什么会这样。好像还好
class func findUsers(text: String)->[User]{ let user = User() var users = [User]() ref.child("Users").queryOrderedByChild("name").queryStartingAtValue(text).observeEventType(.Value, withBlock: { snapshot in for u in snapshot.children{ user.name = u.value!["name"] as? String user.surname = u.value!["surname"] as? String user.email = u.value!["email"] as? String user.score = u.value!["score"] as? Int user.status = u.value!["status"] as? Int user.id = u.value!["id"] as? String user.pin = u.value!["pin"] as? String users.append(user) print(user.name) } }) print("users:", users) return users }
您正在使用queryStartingAtValue。从文档中:
queryStartingAtValue
由FIRDatabaseQuery返回的实例 queryStartingAtValue:childKey将响应节点上具有大于startValue或等于startValue且键大于或等于childKey的值的事件。
FIRDatabaseQuery
queryStartingAtValue:childKey
因此请记住,如果您搜索name某个用户的,则会为所有名称按字母顺序大于给定名称的用户提供。您需要设置a queryEndingAtValue以限制查询范围。
name
queryEndingAtValue
ref.child("Users").queryOrderedByChild("name").queryStartingAtValue(text).queryEndingAtValue(text+"\u{f8ff}")
Firebase旧版文档是了解Firebase如何处理查询的好资源。在那里您会发现:
上面查询中使用的f8ff字符在Unicode范围内是一个很高的代码点。因为它在Unicode中大多数常规字符之后,所以该查询匹配所有以b开头的值。
您可能还会对Elasticsearch感兴趣。Flashlight是一个将Elasticsearch和Firebase集成在一起的节点服务。
如注释所指出的, 如果您搜索的字符串有大写字符, 这 将无效 。在这种情况下,解决方案是 在对象中 有一个 附加字段,其中要搜索的信息全部用小写字母表示 。因此,如果有的话Satoshi Nakamoto,name您可以使用保存其他nameSearch属性satoshi nakamoto。
Satoshi Nakamoto
nameSearch
satoshi nakamoto
最后确保您的搜索字符串也使用小写字母。
您的代码还有其他一些问题。
您正在设置观察者。每当您的数据更改时,它都会触发回调,因此您应该users在回调中重置数组,以确保没有重复和脏数据。
users
由于Firebase调用是异步的,因此您的函数不会向用户返回数据。通话return users时,不会填充用户数组。我建议您使用self.users = users而不是在函数中返回它。否则,如果要继续使用当前方法并将其返回,则应设置完成处理程序。
return users
self.users = users
class func findUsers(text: String)->Void{ ref.child("Users").queryOrderedByChild("name").queryStartingAtValue(text).queryEndingAtValue(text+"\u{f8ff}").observeEventType(.Value, withBlock: { snapshot in var user = User() var users = [User]() for u in snapshot.children{ user.name = u.value!["name"] as? String ... users.append(user) } self.users = users }) }