簡體   English   中英

過濾包含字符串和字符串數組的結構對象

[英]Filtering a struct object containing a string and array of strings

我有一個結構對象,其中包含端口到其各自國家的映射。

struct countryAndPorts {
    var country: String?
    var ports: [String]?
}

我有一個數組var countryAndPortsArray = [countryAndPorts]() ,它保存每個國家的countryAndPort對象。

我還有一個數組var filteredArray = [countryAndPorts]() ,該countryAndPortsArray根據用戶的搜索查詢保存已過濾的countryAndPortsArray對象

我正在使用此功能過濾countryAndPortsArray

func filteredContent(searchKey: String) {
    filteredArray = countryAndPortsArray.filter {
      !($0.ports?.filter{
           $0.range(of: searchKey, options: .caseInsensitive, range: 
           nil, locale: nil) != nil || 
           $0.localizedCaseInsensitiveCompare(searchKey) == .orderedSame
          }.isEmpty ?? true) || 
       $0.country?.localizedCaseInsensitiveContains(searchKey) ?? true
}

我的問題是, filteredArray的結果是包含同一個國家/地區中的每個端口,無論用戶的搜索鍵是否匹配特定端口。

例如,如果用戶搜索“巴黎”,則filteredArray將包含法國的每個端口。 如果用戶搜索“巴塞羅那”,則filteredArray將包含西班牙的每個端口。

期望的結果應僅包含與“巴塞羅那”或“巴黎”匹配的端口,而不應包含同一國家/地區中的所有其他端口。

UPDATE

用例:

var france = countryAndPorts(country: "France", ports: 
["monaco","paris","ajaccio","lyon"])

var spain = countryAndPorts(country: "Spain", ports: ["barcelona", 
"madrid", "catalan"])

var countryAndPortsArray = [france,spain]

如果我在countryAndPortsArray中搜索countryAndPortsArray ,則返回["barcelona", "madrid", "catalan"] 但是我希望它只返回["barcelona"]

這是我的tableview代表,以防萬一它使我的問題更清晰

extension SearchDealsViewController: UITableViewDelegate, 
UITableViewDataSource {

func tableView(_ tableView: UITableView, numberOfRowsInSection section: 
Int) -> Int {
    if let count = filteredArray[section].ports?.count {
        return count
    }
        return 0
}

func tableView(_ tableView: UITableView, cellForRowAt indexPath: 
IndexPath) -> UITableViewCell {
    let cell = tableView.dequeueReusableCell(withIdentifier: "cell", 
for: 
indexPath)

    if let port = filteredArray[indexPath.section].ports?
[indexPath.row] {
        cell.textLabel?.text = port
    }
    cell.textLabel?.font = UIFont.systemFont(ofSize: 10)
    return cell
}

func numberOfSections(in tableView: UITableView) -> Int {
    return filteredArray.count
}

func tableView(_ tableView: UITableView, didSelectRowAt indexPath: 
IndexPath) {
    portsFromTextField.text = filteredArray[indexPath.section].ports?
    [indexPath.row]
}

func tableView(_ tableView: UITableView, viewForHeaderInSection 
section: Int) -> UIView? {
    let header = tableView.dequeueReusableCell(withIdentifier: 
"header")
    let tapSectionHeaderGesture = UITapGestureRecognizer(target: self, 
    action: #selector(getCountryText(sender:)))
    tapSectionHeaderGesture.numberOfTouchesRequired = 1
    tapSectionHeaderGesture.numberOfTapsRequired = 1
    header?.addGestureRecognizer(tapSectionHeaderGesture)

if header != nil {
    header?.textLabel?.textColor = THEME_COLOUR
    header?.textLabel?.font = UIFont.boldSystemFont(ofSize: 12)
    header?.textLabel?.text = filteredArray[section].country
}

return header
}

func getCountryText(sender: UITapGestureRecognizer) {
    if let country = sender.view as? UITableViewCell {
        portsFromTextField.text = country.textLabel?.text
    }
}

func tableView(_ tableView: UITableView, heightForHeaderInSection 
section: Int) -> CGFloat {
    return 30
}

我寫的解決方案,但並不完美。 但是它仍然返回預期結果。

首先,我們可以編輯結構以獲取首選結果。

struct countryAndPorts {
    var country: String?
    var ports: [String]?

    func getPort(_ withName: String) -> [String]? {
        return ports?.filter{$0.lowercased() == withName.lowercased()}
    }
}

比起過濾數據的功能。 它不是完美的,但它可以減少flatMap調用的數量。

func fetch(port withName: String, from ports: [countryAndPorts]) -> [String]? {
    return ports.map{$0.getPort(withName)}.flatMap{$0}.filter{($0?.count)! > 0}.flatMap{$0}.first
}

結果:

fetch(port: "madrid", from: countryAndPortsArray) // ["madrid"]?

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM