求具有字段子集唯一性约束的数据结构的正式名称及实现
带属性唯一性约束的映射结构解答
正式名称
这种数据结构没有绝对统一的专属学名,但通常被称为基于对象属性的唯一键映射,也可描述为带复合唯一键约束的对象注册表。它的核心特征是以对象的指定字段/属性组合作为唯一键,确保键的全局唯一性,绑定对应对象的同时,重复键插入会触发冲突报错,完全对应你类比的「数据库带唯一性约束的表」行为。
编程语言类库实现示例
Java
可以通过现有类库结合自定义逻辑实现:
- 基于
HashMap封装:自定义包含目标属性的复合键类(重写equals和hashCode),或用AbstractMap.SimpleEntry作为键,封装时传入属性提取器生成键,添加前检查键是否存在。 - Guava库的
HashBasedTable:将x作为行键、y作为列键,天然保证(x,y)组合的唯一性,插入重复组合时会抛出IllegalArgumentException。 - Apache Commons Collections的
MultiKeyMap:支持将多个属性作为复合键存储对象,重复键插入时可配置为覆盖或报错。
手动封装简易版示例:
class GamePiece { Integer x; Integer y; String gamePieceType; public GamePiece(Integer x, Integer y, String gamePieceType) { this.x = x; this.y = y; this.gamePieceType = gamePieceType; } public Integer getX() { return x; } public Integer getY() { return y; } } class UniqueKeyMap<T> { private final Map<Object[], T> map = new HashMap<>(); private final Function<T, Object>[] keyExtractors; @SafeVarargs public UniqueKeyMap(Function<T, Object>... keyExtractors) { this.keyExtractors = keyExtractors; } public void add(T item) { Object[] key = Arrays.stream(keyExtractors).map(f -> f.apply(item)).toArray(); if (map.containsKey(key)) { throw new IllegalArgumentException("Duplicate key: " + Arrays.toString(key)); } map.put(key, item); } } // 使用示例 UniqueKeyMap<GamePiece> gameMap = new UniqueKeyMap<>(GamePiece::getX, GamePiece::getY); gameMap.add(new GamePiece(1, 1, "Knight")); gameMap.add(new GamePiece(1, 1, "Rook")); // 抛出异常
C#
- 利用
Dictionary<TKey, TValue>,使用ValueTuple<int, int>作为复合键,插入前检查键是否存在:
public class GamePiece { public int X { get; set; } public int Y { get; set; } public string GamePieceType { get; set; } } var gameMap = new Dictionary<(int, int), GamePiece>(); var knight = new GamePiece { X = 1, Y = 1, GamePieceType = "Knight" }; gameMap.Add((knight.X, knight.Y), knight); var rook = new GamePiece { X = 1, Y = 1, GamePieceType = "Rook" }; if (gameMap.ContainsKey((rook.X, rook.Y))) { throw new ArgumentException("Duplicate key (1,1)"); }
- 也可使用Immutable Collections中的
ImmutableDictionary,同样支持复合键的唯一性约束。
Python
直接用dict结合元组作为键,或封装成类:
class GamePiece: def __init__(self, x, y, game_piece_type): self.x = x self.y = y self.game_piece_type = game_piece_type class UniqueKeyMap: def __init__(self, *key_getters): self.key_getters = key_getters self.map = {} def add(self, item): key = tuple(getter(item) for getter in self.key_getters) if key in self.map: raise ValueError(f"Duplicate key: {key}") self.map[key] = item # 使用示例 game_map = UniqueKeyMap(lambda p: p.x, lambda p: p.y) game_map.add(GamePiece(1, 1, "Knight")) game_map.add(GamePiece(1, 1, "Rook")) # 抛出异常
内容的提问来源于stack exchange,提问作者IndustryUser1942
相关产品推荐
相关产品推荐

