Ios 在tableView swift4中搜索JSON数据

Ios 在tableView swift4中搜索JSON数据,ios,swift,uisearchbar,Ios,Swift,Uisearchbar,我试图在表视图中显示jsondata并从搜索栏中搜索country,但在textDidChange功能中获得error 我希望用户在搜索栏中输入三个单词,然后表格视图将打开并搜索数据 struct country : Decodable { let name : String let capital : String let region : String } class ViewController: UIViewController,UISearchBarDel

我试图在
表视图中显示
jsondata
并从
搜索栏中搜索
country
,但在
textDidChange
功能中获得
error

我希望用户在
搜索栏
中输入三个单词,然后
表格视图
将打开并搜索数据

struct country : Decodable {
    let name : String
    let capital : String
    let region : String
  }

class ViewController: UIViewController,UISearchBarDelegate {

    var isSearch : Bool = false
    var countries = [country]()
    var arrFilter:[String] = []

    @IBOutlet weak var tableview: UITableView!
    @IBOutlet weak var searchbar: UISearchBar!

    override func viewDidLoad() {
        super.viewDidLoad()

        tableview.dataSource = self
        tableview.delegate = self
        searchbar.delegate = self

        let jsonurl = "https://restcountries.eu/rest/v2/all"
        let url = URL(string: jsonurl)

        URLSession.shared.dataTask(with: url!) { (data, response, error) in

            do{
                self.countries = try JSONDecoder().decode([country].self, from: data!)

            }
            catch{
                print("Error")
            }
            DispatchQueue.main.async {
                self.tableview.reloadData()
            }
            }.resume()
}
显示此部分的错误

func searchBar(searchBar: UISearchBar, textDidChange searchText: String) {

    if searchText.characters.count == 0 {
        isSearch = false;
        self.tableview.reloadData()
    } else {
        arrFilter = countries.filter({ (text) -> Bool in
            let tmp: NSString = text
            let range = tmp.rangeOfString(searchText, options: NSStringCompareOptions.CaseInsensitiveSearch)
            return range.location != NSNotFound
        })
        if(arrFilter.count == 0){
            isSearch = false;
        } else {
            isSearch = true;
        }
        self.tableview.reloadData()
    }
  }

}
我的表格视图部分

extension ViewController : UITableViewDelegate, UITableViewDataSource{
  func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
    if(isSearch){
       return arrFilter.count
    }
    else{
      return countries.coun
    }
}

func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {

    let cell = tableview.dequeueReusableCell(withIdentifier: "cell", for: indexPath)
    if(isSearch){    
         cell.textLabel?.text = arrFilter[indexPath.row]    
    }else{
         cell.textLabel?.text = countries[indexPath.row].name.capitalized
    }
    return cell
  }
}

您正在以字符串形式获取数组的country对象,因此发生了这样的错误。。 请按以下步骤操作

    var arrFilter:[country] = [country]()

    func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {

        let cell = tableview.dequeueReusableCell(withIdentifier: "cell", for: indexPath)
        if(isSearch){    
        cell.textLabel?.text = arrFilter[indexPath.row].name.capitalized    
        }else{
             cell.textLabel?.text = countries[indexPath.row].name.capitalized
        }
        return cell
    }


    func searchBar(_ searchBar: UISearchBar, textDidChange searchText: String) {
            if searchText.characters.count == 0 {
                isSearch = false;
                self.tableview.reloadData()
            } else {
                arrFilter = countries.filter({ (country) -> Bool in

                    let tmp: NSString = NSString.init(string: country.name)
                    let range = tmp.range(of: searchText, options: NSString.CompareOptions.caseInsensitive)

                    return range.location != NSNotFound
                })
                if(arrFilter.count == 0){
                    isSearch = false;
                } else {
                    isSearch = true;
                }
                self.tableview.reloadData()
            }
     }

首先,您不能将值类型[Country]分配给[String]。例如,在当时分配arrFilter时,Country.filter始终返回国家类型值而不是字符串类型

使用下面的代码来帮助您

var countries = [country]()
var arrFilter:[country] = [country]()
在视图中加载

override func viewDidLoad() {

    self.countries.append(country(name: "India", capital: "New Delhi", region: "Asia"))
    self.countries.append(country(name: "Indonesia", capital: "Jakarta", region: "region"))
    self.countries.append(country(name: "Australia", capital: "Canberra", region: "Austrialia"))
    // Do any additional setup after loading the view.
}

谢谢

  • 首先不要在Swift
    Foundation
    rangeOfString
    API中使用
    NSString
    ,使用本机
    String
    和本机
    范围(of
  • 其次,永远不要使用
    检查空字符串和空数组。count==0
    。存在
    isEmpty
  • 第三,请用大写字母命名结构和类。
    struct Country…

出现此错误是因为您正在筛选
国家
实例,并且实际上您正在查找其
名称
或其
地区

这是您的代码的纯Swift版本

func searchBar(searchBar: UISearchBar, textDidChange searchText: String) {

    if searchText.isEmpty {
        isSearch = false
    } else {
        arrFilter = countries.filter( $0.name.range(of: searchText, options: .caseInsensitive) != nil }
        isSearch = !arrFilter.isEmpty 
    }
    self.tableview.reloadData()
}
如果要筛选
名称
区域
写入

arrFilter = countries.filter( $0.name.range(of: searchText, options: .caseInsensitive) != nil 
                              || $0.region.range(of: searchText, options: .caseInsensitive) != nil }
let dataArray = isSearch ? arrFilter : countries
cell.textLabel?.text = dataArray[indexPath.row].name.capitalized 
使用此语法声明
arrFilter

var arrFilter = [Country]()
并在
cellForRow
write中

arrFilter = countries.filter( $0.name.range(of: searchText, options: .caseInsensitive) != nil 
                              || $0.region.range(of: searchText, options: .caseInsensitive) != nil }
let dataArray = isSearch ? arrFilter : countries
cell.textLabel?.text = dataArray[indexPath.row].name.capitalized 


发生了什么错误?无法将类型“country”的值转换为指定的类型“NSString”此错误转换为此函数func searchBar(searchBar:UISearchBar,textDidChange searchText:String)Countries是一个结构数组,而不是字符串。请尝试此
arrFilter=Countries.filter{$0.name.localizedLowercase.localizedCaseInsensitiveContains(searchText)}作为数组
,但arrayfilter是字符串数组。无法将“[country]”类型的值分配给“[string]类型'此错误显示在else部分的第一行它在tmp变量中显示错误,如此无法将'String'类型的值转换为指定类型的'NSString',如果将'NSString'转换为'String',则在范围变量中显示错误。更新答案。错误删除但搜索栏不工作意味着?方法未调用?写入方法未在搜索栏中调用so不适用于搜索但我的范围部分是什么,因为它显示了该部分中的错误,例如类型为“String”的值没有成员“rangeOfString”@sohan123,如果您的目的是只显示搜索数据,那么为什么返回范围?在您的文本中,我放置了我的“searchtext”,并进行了如上所述的更改,但没有打印到range.location和temp中。我认为func不call@sohan123请使用瓦迪亚代码进行筛选:-arrFilter=countries.filter($0.name.range(of:searchText,options:.casesensitive)!=nil | |$0.region.range(of:searchText,options:.casesensitive)!=nil}@sohan123您需要筛选数据或范围,或两者都需要?搜索栏的任何方法都不起作用。我将uisearchbar放入outlet并将委托给搜索栏。但仍然是所有方法(函数)不工作。在方法中放置断点并检查。我的答案将修复警告和错误,并显示一些代码改进。
UISearchBar
设置是另一个问题。