好的,我已经在obj C中看过以前的问题并尝试过。我试图构建的是类似于iphone的联系人应用程序。我在表格中插入行时出现此问题。之前我从未遇到过插入行的问题,我可能认为这是因为我的数据结构不好?
我尝试的解决方案是tableView.beginUpdates和endUpdates,但仍然是同样的错误。这是我的联系人列表代码。
class ContactsListViewController: UITableViewController, AddContactViewControllerDelegate {
let cellID = "contactCellID"
var sectionNames = ["A","B","C","D"]
var name = [0: ["Amber", "Ajay", "Abhishek", "Anshul"], 1: ["Borat", "Bruno", "Billooo"], 2: ["Chinku","Champu","Champak"], 3: ["Daya", "Divya","Delhi Police"]]
//
// @IBOutlet weak var addBarOutlet: UIBarButtonItem!
// @IBAction func addBarButton(sender: UIBarButtonItem) {
// performSegueWithIdentifier("AddItemSegueID", sender: addBarOutlet)
// }
//
//var nameSet = ["0": "Amber", "1": "Blah", "2": "Chris" ]
override func numberOfSectionsInTableView(tableView: UITableView) -> Int {
return name.count
}
override func tableView(tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
let array = name[section]
return (array!.count)
}
override func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell {
let cell = tableView.dequeueReusableCellWithIdentifier(cellID, forIndexPath: indexPath)
let nameArray = name[indexPath.section]
// guard let nameArray = name[indexPath.section] else {
// print("Invalid ")
// cell.textLabel?.text = "Not Found"
// return cell
// }
cell.textLabel?.text = nameArray![indexPath.row]
return cell
}
override func tableView(tableView: UITableView, titleForHeaderInSection section: Int) -> String? {
var Keys = [Int] (name.keys)
Keys.sortInPlace()
let value = Keys[section]
var sec = ""
if value == Keys[section] {
sec = sectionNames[section]
}
return sec
}
override func tableView(tableView: UITableView, didSelectRowAtIndexPath indexPath: NSIndexPath) {
tableView.deselectRowAtIndexPath(indexPath, animated: true)
}
override func prepareForSegue(segue: UIStoryboardSegue, sender: AnyObject?) {
if segue.identifier == "AddItemSegueID" {
// let navcontroller = segue.destinationViewController as! UINavigationController
// let controller = navcontroller.topViewController as! AddContactViewController
let controller = segue.destinationViewController as! AddContactViewController
controller.delegate = self
}
}
func addContactViewController(controller: AddContactViewController, didFinishAdding item: ContactNames) {
//var dictKeys = [Int](name.keys)
let newName = item.text
let firstIndex = newName.startIndex
//let firstChar = newName[firstIndex]
var check = name[0]!
let newRowIndex = check.count
check.append(newName)
tableView.beginUpdates()
let indexPath = NSIndexPath(forRow: newRowIndex, inSection: 0)
let indexPaths = [indexPath]
tableView.insertRowsAtIndexPaths(indexPaths, withRowAnimation: .Automatic)
tableView.endUpdates()
dismissViewControllerAnimated(true, completion: nil)
}
func addContactViewControllerDidCancel(controller: AddContactViewController) {
dismissViewControllerAnimated(true, completion: nil)
}
}
ContactNames是一个普通的swift类,它包含一个字符串属性。 另一件事是我在AddItemVC中实现了一个协议,以便将数据发送回过去的视图控制器,所以我做了一个我最近也学到的委托。继承人加上我的意见:
protocol AddContactViewControllerDelegate: class {
func addContactViewControllerDidCancel(controller: AddContactViewController)
func addContactViewController(controller: AddContactViewController, didFinishAdding item: ContactNames)
}
class AddContactViewController: UIViewController, UITextFieldDelegate {
weak var delegate: AddContactViewControllerDelegate?
@IBOutlet weak var nameField: UITextField!
@IBOutlet weak var doneOutlet: UIBarButtonItem!
var contactList = ContactsListViewController()
override func viewDidLoad() {
nameField.becomeFirstResponder()
self.tabBarController?.tabBar.hidden = true
doneOutlet.enabled = false
}
override func touchesBegan(touches: Set<UITouch>, withEvent event: UIEvent?) {
nameField.resignFirstResponder()
}
func textField(textField: UITextField, shouldChangeCharactersInRange range: NSRange, replacementString string: String) -> Bool {
let oldText: NSString = textField.text!
let newText: NSString = oldText.stringByReplacingCharactersInRange(range, withString: string)
doneOutlet.enabled = (newText.length>0)
// if newText.length > 0 {
// doneOutlet.enabled = true
// }else {
// doneOutlet.enabled = false
// }
return true
}
@IBAction func saveAction(sender: UIBarButtonItem) {
let newItem = ContactNames()
newItem.text = nameField.text!
delegate?.addContactViewController(self, didFinishAdding: newItem)
}
@IBAction func cancelAction(sender: UIBarButtonItem) {
delegate?.addContactViewControllerDidCancel(self)
}
}
此外,如果您为此建议更好的数据结构。
答案 0 :(得分:0)
Swift中的本机集合类型是值类型,这意味着当您获得键或索引的值时,始终会复制对象。
为键分配数组&#34; 0&#34;变量check
并附加值
var check = name[0]!
...
check.append(newName)
但不会更改字典name
中的原始数组。
您需要将数组分配回字典
name[0] = check
使用密钥的实际字母而不是不相关的数字是否更方便?
答案 1 :(得分:0)
在beginUpdates和endUpdates之间,您需要更新数据源,使其与insertRowsAtIndexPaths等操作相匹配。因此,如果您有四行,并且插入一行,那么您的数据源也必须更改为现在有五行。正如错误消息所说的那样。