001// License: GPL. For details, see LICENSE file. 002package org.openstreetmap.josm.data.osm; 003 004import java.util.HashMap; 005import java.util.HashSet; 006import java.util.Iterator; 007import java.util.Map; 008import java.util.Set; 009import java.util.Map.Entry; 010 011import org.openstreetmap.josm.data.osm.history.HistoryOsmPrimitive; 012import org.openstreetmap.josm.tools.CheckParameterUtil; 013 014/** 015 * A ChangesetDataSet holds the content of a changeset. 016 */ 017public class ChangesetDataSet { 018 019 public static enum ChangesetModificationType { 020 CREATED, 021 UPDATED, 022 DELETED 023 } 024 025 public static interface ChangesetDataSetEntry { 026 public ChangesetModificationType getModificationType(); 027 public HistoryOsmPrimitive getPrimitive(); 028 } 029 030 private final Map<PrimitiveId, HistoryOsmPrimitive> primitives = new HashMap<>(); 031 private final Map<PrimitiveId, ChangesetModificationType> modificationTypes = new HashMap<>(); 032 033 /** 034 * Remembers a history primitive with the given modification type 035 * 036 * @param primitive the primitive. Must not be null. 037 * @param cmt the modification type. Must not be null. 038 * @throws IllegalArgumentException thrown if primitive is null 039 * @throws IllegalArgumentException thrown if cmt is null 040 */ 041 public void put(HistoryOsmPrimitive primitive, ChangesetModificationType cmt) throws IllegalArgumentException{ 042 CheckParameterUtil.ensureParameterNotNull(primitive,"primitive"); 043 CheckParameterUtil.ensureParameterNotNull(cmt,"cmt"); 044 primitives.put(primitive.getPrimitiveId(), primitive); 045 modificationTypes.put(primitive.getPrimitiveId(), cmt); 046 } 047 048 /** 049 * Replies true if the changeset content contains the object with primitive <code>id</code>. 050 * @param id the id. 051 * @return true if the changeset content contains the object with primitive <code>id</code> 052 */ 053 public boolean contains(PrimitiveId id) { 054 if (id == null) return false; 055 return primitives.containsKey(id); 056 } 057 058 /** 059 * Replies the modification type for the object with id <code>id</code>. Replies null, if id is null or 060 * if the object with id <code>id</code> isn't in the changeset content. 061 * 062 * @param id the id 063 * @return the modification type 064 */ 065 public ChangesetModificationType getModificationType(PrimitiveId id) { 066 if (!contains(id)) return null; 067 return modificationTypes.get(id); 068 } 069 070 /** 071 * Replies true if the primitive with id <code>id</code> was created in this 072 * changeset. Replies false, if id is null. 073 * 074 * @param id the id 075 * @return true if the primitive with id <code>id</code> was created in this 076 * changeset. 077 */ 078 public boolean isCreated(PrimitiveId id) { 079 if (!contains(id)) return false; 080 return ChangesetModificationType.CREATED.equals(getModificationType(id)); 081 } 082 083 /** 084 * Replies true if the primitive with id <code>id</code> was updated in this 085 * changeset. Replies false, if id is null. 086 * 087 * @param id the id 088 * @return true if the primitive with id <code>id</code> was updated in this 089 * changeset. 090 */ 091 public boolean isUpdated(PrimitiveId id) { 092 if (!contains(id)) return false; 093 return ChangesetModificationType.UPDATED.equals(getModificationType(id)); 094 } 095 096 /** 097 * Replies true if the primitive with id <code>id</code> was deleted in this 098 * changeset. Replies false, if id is null. 099 * 100 * @param id the id 101 * @return true if the primitive with id <code>id</code> was deleted in this 102 * changeset. 103 */ 104 public boolean isDeleted(PrimitiveId id) { 105 if (!contains(id)) return false; 106 return ChangesetModificationType.DELETED.equals(getModificationType(id)); 107 } 108 109 /** 110 * Replies the set of primitives with a specific modification type 111 * 112 * @param cmt the modification type. Must not be null. 113 * @return the set of primitives 114 * @throws IllegalArgumentException thrown if cmt is null 115 */ 116 public Set<HistoryOsmPrimitive> getPrimitivesByModificationType(ChangesetModificationType cmt) throws IllegalArgumentException { 117 CheckParameterUtil.ensureParameterNotNull(cmt,"cmt"); 118 HashSet<HistoryOsmPrimitive> ret = new HashSet<>(); 119 for (Entry<PrimitiveId, ChangesetModificationType> entry: modificationTypes.entrySet()) { 120 if (entry.getValue().equals(cmt)) { 121 ret.add(primitives.get(entry.getKey())); 122 } 123 } 124 return ret; 125 } 126 127 /** 128 * Replies the number of objects in the dataset 129 * 130 * @return the number of objects in the dataset 131 */ 132 public int size() { 133 return primitives.size(); 134 } 135 136 /** 137 * Replies the {@link HistoryOsmPrimitive} with id <code>id</code> from this 138 * dataset. null, if there is no such primitive in the data set. 139 * 140 * @param id the id 141 * @return the {@link HistoryOsmPrimitive} with id <code>id</code> from this 142 * dataset 143 */ 144 public HistoryOsmPrimitive getPrimitive(PrimitiveId id) { 145 if (id == null) return null; 146 return primitives.get(id); 147 } 148 149 public Iterator<ChangesetDataSetEntry> iterator() { 150 return new DefaultIterator(); 151 } 152 153 private static class DefaultChangesetDataSetEntry implements ChangesetDataSetEntry { 154 private ChangesetModificationType modificationType; 155 private HistoryOsmPrimitive primitive; 156 157 public DefaultChangesetDataSetEntry(ChangesetModificationType modificationType, HistoryOsmPrimitive primitive) { 158 this.modificationType = modificationType; 159 this.primitive = primitive; 160 } 161 162 @Override 163 public ChangesetModificationType getModificationType() { 164 return modificationType; 165 } 166 167 @Override 168 public HistoryOsmPrimitive getPrimitive() { 169 return primitive; 170 } 171 } 172 173 private class DefaultIterator implements Iterator<ChangesetDataSetEntry> { 174 private Iterator<Entry<PrimitiveId, ChangesetModificationType>> typeIterator; 175 176 public DefaultIterator() { 177 typeIterator = modificationTypes.entrySet().iterator(); 178 } 179 180 @Override 181 public boolean hasNext() { 182 return typeIterator.hasNext(); 183 } 184 185 @Override 186 public ChangesetDataSetEntry next() { 187 Entry<PrimitiveId, ChangesetModificationType> next = typeIterator.next(); 188 ChangesetModificationType type = next.getValue(); 189 HistoryOsmPrimitive primitive = primitives.get(next.getKey()); 190 return new DefaultChangesetDataSetEntry(type, primitive); 191 } 192 193 @Override 194 public void remove() { 195 throw new UnsupportedOperationException(); 196 } 197 } 198}