-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy patharray_hash_map.zig
162 lines (141 loc) · 5.02 KB
/
array_hash_map.zig
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
// File: array_hash_map.zig
// Created Time: 2023-01-15
// Author: sjinzh (sjinzh@gmail.com)
const std = @import("std");
const inc = @import("include");
// 键值对
const Pair = struct {
key: usize = undefined,
val: []const u8 = undefined,
pub fn init(key: usize, val: []const u8) Pair {
return Pair {
.key = key,
.val = val,
};
}
};
// 基于数组简易实现的哈希表
pub fn ArrayHashMap(comptime T: type) type {
return struct {
bucket: ?std.ArrayList(?T) = null,
mem_allocator: std.mem.Allocator = undefined,
const Self = @This();
// 构造函数
pub fn init(self: *Self, allocator: std.mem.Allocator) !void {
self.mem_allocator = allocator;
// 初始化一个长度为 100 的桶(数组)
self.bucket = std.ArrayList(?T).init(self.mem_allocator);
var i: i32 = 0;
while (i < 100) : (i += 1) {
try self.bucket.?.append(null);
}
}
// 析构函数
pub fn deinit(self: *Self) void {
if (self.bucket != null) self.bucket.?.deinit();
}
// 哈希函数
fn hashFunc(key: usize) usize {
var index = key % 100;
return index;
}
// 查询操作
pub fn get(self: *Self, key: usize) []const u8 {
var index = hashFunc(key);
var pair = self.bucket.?.items[index];
return pair.?.val;
}
// 添加操作
pub fn put(self: *Self, key: usize, val: []const u8) !void {
var pair = Pair.init(key, val);
var index = hashFunc(key);
self.bucket.?.items[index] = pair;
}
// 删除操作
pub fn remove(self: *Self, key: usize) !void {
var index = hashFunc(key);
// 置为 null ,代表删除
self.bucket.?.items[index] = null;
}
// 获取所有键值对
pub fn pairSet(self: *Self) !std.ArrayList(T) {
var entry_set = std.ArrayList(T).init(self.mem_allocator);
for (self.bucket.?.items) |item| {
if (item == null) continue;
try entry_set.append(item.?);
}
return entry_set;
}
// 获取所有键
pub fn keySet(self: *Self) !std.ArrayList(usize) {
var key_set = std.ArrayList(usize).init(self.mem_allocator);
for (self.bucket.?.items) |item| {
if (item == null) continue;
try key_set.append(item.?.key);
}
return key_set;
}
// 获取所有值
pub fn valueSet(self: *Self) !std.ArrayList([]const u8) {
var value_set = std.ArrayList([]const u8).init(self.mem_allocator);
for (self.bucket.?.items) |item| {
if (item == null) continue;
try value_set.append(item.?.val);
}
return value_set;
}
// 打印哈希表
pub fn print(self: *Self) !void {
var entry_set = try self.pairSet();
defer entry_set.deinit();
for (entry_set.items) |item| {
std.debug.print("{} -> {s}\n", .{item.key, item.val});
}
}
};
}
// Driver Code
pub fn main() !void {
// 初始化哈希表
var map = ArrayHashMap(Pair){};
try map.init(std.heap.page_allocator);
defer map.deinit();
// 添加操作
// 在哈希表中添加键值对 (key, value)
try map.put(12836, "小哈");
try map.put(15937, "小啰");
try map.put(16750, "小算");
try map.put(13276, "小法");
try map.put(10583, "小鸭");
std.debug.print("\n添加完成后,哈希表为\nKey -> Value\n", .{});
try map.print();
// 查询操作
// 向哈希表输入键 key ,得到值 value
var name = map.get(15937);
std.debug.print("\n输入学号 15937 ,查询到姓名 {s}\n", .{name});
// 删除操作
// 在哈希表中删除键值对 (key, value)
try map.remove(10583);
std.debug.print("\n删除 10583 后,哈希表为\nKey -> Value\n", .{});
try map.print();
// 遍历哈希表
std.debug.print("\n遍历键值对 Key->Value\n", .{});
var entry_set = try map.pairSet();
for (entry_set.items) |kv| {
std.debug.print("{} -> {s}\n", .{kv.key, kv.val});
}
defer entry_set.deinit();
std.debug.print("\n单独遍历键 Key\n", .{});
var key_set = try map.keySet();
for (key_set.items) |key| {
std.debug.print("{}\n", .{key});
}
defer key_set.deinit();
std.debug.print("\n单独遍历值 value\n", .{});
var value_set = try map.valueSet();
for (value_set.items) |val| {
std.debug.print("{s}\n", .{val});
}
defer value_set.deinit();
_ = try std.io.getStdIn().reader().readByte();
}