Edit in JSFiddle

//wrapper for an observable that protects value until committed
ko.protectedObservable = function(initialValue) {
    //private variables
    var _temp = initialValue;
    var _actual = ko.observable(initialValue);

    var result = ko.dependentObservable({
        read: _actual,
        write: function(newValue) {
            _temp = newValue;
        }
    }).extend({ notify: "always" }); //needed in KO 3.0+ for reset, as computeds no longer notify when value is the same
    
    //commit the temporary value to our observable, if it is different
    result.commit = function() {
        if (_temp !== _actual()) {
            _actual(_temp);
        }
    };

    //notify subscribers to update their value with the original
    result.reset = function() {
        _actual.valueHasMutated();
        _temp = _actual();
    };

    return result;
};

//construct an Item

var Item = function(name, quantity) {
    this.name = ko.protectedObservable(name);
    this.quantity = ko.protectedObservable(quantity);
}

var ViewModel = function(items) {
    var self = this;
    
    this.items = ko.observableArray(items);
   
    this.selectedItem = ko.observable();

    this.addItem = function() {
        var newItem = new Item("new item", 0);
        self.items.push(newItem);
        self.selectedItem(newItem);
    };

    this.deleteItem = function(itemToDelete) {
        self.items.remove(itemToDelete);
        self.selectedItem(null);
    };

    this.editItem = function(item) {
        self.selectedItem(item);
    };

    this.acceptItemEdit = function() {
        self.selectedItem().name.commit();
        self.selectedItem().quantity.commit();
        self.selectedItem(null);
    };

    this.cancelItemEdit = function() {
        self.selectedItem().name.reset();
        self.selectedItem().quantity.reset();
        self.selectedItem(null);
    };

    this.templateToUse = function(item) {
        return self.selectedItem() === item ? "editTmpl" : "itemTmpl";
    };
};
    
ko.applyBindings(new ViewModel([
    new Item("one", 1),
    new Item("two", 2),
    new Item("three", 3)
    ]));
<table>
    <tr>
        <th>Name</th>
        <th>Quantity</th>
        <th></th>
        <th></th>
    </tr>            
    <tbody data-bind="template: { name: templateToUse, foreach: items}"></tbody>
</table>

<script id="itemTmpl" type="text/html">
    <tr>
        <td data-bind="text: name"></td>
        <td data-bind="text: quantity"></td>
        <td class="buttons">
            <button data-bind="click: $root.editItem">Edit</button>
            <button data-bind="click: $root.deleteItem">Delete</button>

        </td>
    </tr>
</script>

<button data-bind="click: addItem">New Item</button>

<script id="editTmpl" type="text/html">
    <tr>
        <td>
            <input data-bind="value: name" />
        </td>
        <td>
            <input data-bind="value: quantity" />
        </td>
        <td class="buttons">
            <button data-bind="click: $root.acceptItemEdit">Accept</button>
            <button data-bind="click: $root.cancelItemEdit">Cancel</button>
        </td>
    </tr>
</script>
input { width: 75px; }
td { width: 75px; }
th { color: #666; font-size: .8em; }
.buttons { width: 150px; }