【问题标题】:Deleting item in tableView by removing item from array crashes with fatal error: Index out of range通过从数组中删除项目来删除 tableView 中的项目时出现致命错误:索引超出范围
【发布时间】:2018-01-15 16:54:24
【问题描述】:

我正在尝试从 tableview 中显示的公共静态数组中删除一个项目。删除发生在不同的视图控制器中,当我尝试进入该视图控制器时,应用程序崩溃并出现“索引超出范围”的错误

这是我删除项目的地方

func removeItem (info:Dictionary<String, Any>){
    let stringKey = info[KEYS.stringKey] as! String
    for var i in 0 ..< ItemsViewController.itemVideosList.count {

        let current = ItemsViewController.itemVideosList[i]
        let currentStringKey = current[KEYS.stringKey] as! String

        if stringKey == currentStringKey {

            ItemsViewController.itemVideosList.remove(at: i)
            return
        }
    }

我在一个按钮上调用这个方法点击这里:

@IBAction func FavoriteAction(_ sender: Any) {


    if Flag {
        removeFromFavorite(info: songInfo)
        Flag = false
        }
    else {
        ItemsViewController.itemVideosList.insert(songInfo, at: 0)
        favFlag = true
    }
}

我正在使用此方法在“ItemsViewController”viewDidLoad 中填充表格视图

func loadItems() {
    DispatchQueue.main.async {
        self.itemsTableView.reloadData()
    }
}

谢谢

【问题讨论】:

  • 删除后重新加载表。问题可能是其他问题,但也不确定。
  • 我在哪里重新加载表格?我无法从删除方法中获得对表的引用

标签: ios arrays swift uitableview


【解决方案1】:

您在删除时尝试循环。这会导致 ItemsViewController.itemVideosList.count 在您删除后无效。

  1. 你可以简单地通过添加一个 break 而不是 return 来解决你的问题

    if stringKey == currentStringKey {
        ItemsViewController.itemVideosList.remove(at: i)
        return
    }
    
  2. 更重要的是,您不应该在迭代时修改集合。这会导致不希望的副作用。最好只存储 indexToDelete,然后在循环外将其删除。

    func removeItem (info:Dictionary<String, Any>){
    let indexToRemove = -1
    let stringKey = info[KEYS.stringKey] as! String
    for var i in 0 ..< ItemsViewController.itemVideosList.count {
    
        let current = ItemsViewController.itemVideosList[i]
        let currentStringKey = current[KEYS.stringKey] as! String
    
        if stringKey == currentStringKey {
            indexToDelete = i            
            break
        }
    }
    
    ItemsViewController.itemVideosList.remove(at: indexToDelete)
    }
    

注意:

您可以使用这样的高阶函数使您的迭代更清晰:

var list = ["a", "b", "c"]

let index = list.index { (str) -> Bool in
    if str == "b" {
        return true
    }
    return false
}

【讨论】:

  • 我认为问题出在我重新加载 tableview 时。 (尽管您的回答对我也很重要)。我添加的打印显示该项目已被删除,但是当我尝试重新进入视图控制器时它崩溃了。
  • @IttaiOren 删除后你是在同一个控制器上还是在执行一些 segue?
  • @Tushar Sharma 我在同一个控制器上。删除会删除静态列表中的一个项目,当用户选择转到该控制器时,该列表将填充 tableview
  • 你可以发布一个通知,让其他 viewController 监听。然后重新加载数据
  • 你能给我一个关于这种通知和监听器的例子吗?
猜你喜欢
  • 1970-01-01
  • 2015-12-28
  • 2020-03-27
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多