package de.mpicbg.knime.knutils; import org.knime.core.data.*; import org.knime.core.data.container.CellFactory; import org.knime.core.data.container.ColumnRearranger; import org.knime.core.data.container.SingleCellFactory; import java.util.*; /** * Document me! * * @author Holger Brandl */ public class TableUpdateCache { private Map<Attribute, Map<RowKey, DataCell>> cache = new LinkedHashMap<Attribute, Map<RowKey, DataCell>>(); private DataTableSpec dataTableSpec; private Collection<String> deleteColumns = new HashSet<String>(); public TableUpdateCache(DataTableSpec dataTableSpec) { this.dataTableSpec = dataTableSpec; } public void add(DataRow dataRow, Attribute attribute, DataCell dataCell) { registerAttribute(attribute); cache.get(attribute).put(dataRow.getKey(), dataCell); } public void registerAttributes(List<Attribute> layoutAttributes) { for (Attribute layoutAttribute : layoutAttributes) { registerAttribute(layoutAttribute); } } public void registerAttribute(Attribute attribute) { if (!cache.keySet().contains(attribute)) { cache.put(attribute, new HashMap<RowKey, DataCell>()); } } public ColumnRearranger createColRearranger() { ColumnRearranger c = new ColumnRearranger(dataTableSpec); // column spec of the appended column List<Attribute> existingAttributes = AttributeUtils.convert(dataTableSpec); for (final Attribute attribute : cache.keySet()) { // create a factory for each new attribute to be appended String newAttributeName = attribute.getName(); DataColumnSpec attributeSpec = attribute.getColumnSpec(); CellFactory factory = new SingleCellFactory(attributeSpec) { public DataCell getCell(DataRow row) { Map<RowKey, DataCell> map = cache.get(attribute); DataCell dataCell = map.get(row.getKey()); if (dataCell != null) { return dataCell; } else { return DataType.getMissingCell(); } } }; if (AttributeUtils.contains(existingAttributes, newAttributeName)) { c.replace(factory, newAttributeName); } else { c.append(factory); } } // delete all columns scheduled for removal c.remove(deleteColumns.toArray(new String[deleteColumns.size()])); return c; } public void registerDeleteColumn(String columnName) { deleteColumns.add(columnName); } }