Skip to content

Commit 0f72b19

Browse files
committed
Upload note code of chapter 5 associated container
1 parent 198cd9b commit 0f72b19

11 files changed

+2449
-0
lines changed

5_STL_associated_container/5_7_2_stl_hashtable.h

Lines changed: 1101 additions & 0 deletions
Large diffs are not rendered by default.
Lines changed: 96 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,96 @@
1+
/*
2+
* Copyright (c) 1996-1998
3+
* Silicon Graphics Computer Systems, Inc.
4+
*
5+
* Permission to use, copy, modify, distribute and sell this software
6+
* and its documentation for any purpose is hereby granted without fee,
7+
* provided that the above copyright notice appear in all copies and
8+
* that both that copyright notice and this permission notice appear
9+
* in supporting documentation. Silicon Graphics makes no
10+
* representations about the suitability of this software for any
11+
* purpose. It is provided "as is" without express or implied warranty.
12+
*
13+
*
14+
* Copyright (c) 1994
15+
* Hewlett-Packard Company
16+
*
17+
* Permission to use, copy, modify, distribute and sell this software
18+
* and its documentation for any purpose is hereby granted without fee,
19+
* provided that the above copyright notice appear in all copies and
20+
* that both that copyright notice and this permission notice appear
21+
* in supporting documentation. Hewlett-Packard Company makes no
22+
* representations about the suitability of this software for any
23+
* purpose. It is provided "as is" without express or implied warranty.
24+
*
25+
*/
26+
27+
/* NOTE: This is an internal header file, included by other STL headers.
28+
* You should not attempt to use it directly.
29+
*/
30+
31+
#ifndef __SGI_STL_HASH_FUN_H
32+
#define __SGI_STL_HASH_FUN_H
33+
34+
#include <stddef.h>
35+
36+
__STL_BEGIN_NAMESPACE
37+
38+
// 以下都是用仿函数实现hash function,重载不同数据类型
39+
40+
template <class _Key> struct hash { };
41+
42+
// 为字符串进行散列
43+
inline size_t __stl_hash_string(const char* __s)
44+
{
45+
unsigned long __h = 0;
46+
for ( ; *__s; ++__s)
47+
__h = 5*__h + *__s; // 采用元素层次相加
48+
49+
return size_t(__h);
50+
}
51+
52+
__STL_TEMPLATE_NULL struct hash<char*>
53+
{
54+
size_t operator()(const char* __s) const { return __stl_hash_string(__s); }
55+
};
56+
57+
__STL_TEMPLATE_NULL struct hash<const char*>
58+
{
59+
size_t operator()(const char* __s) const { return __stl_hash_string(__s); }
60+
};
61+
62+
__STL_TEMPLATE_NULL struct hash<char> {
63+
size_t operator()(char __x) const { return __x; }
64+
};
65+
__STL_TEMPLATE_NULL struct hash<unsigned char> {
66+
size_t operator()(unsigned char __x) const { return __x; }
67+
};
68+
__STL_TEMPLATE_NULL struct hash<signed char> {
69+
size_t operator()(unsigned char __x) const { return __x; }
70+
};
71+
__STL_TEMPLATE_NULL struct hash<short> {
72+
size_t operator()(short __x) const { return __x; }
73+
};
74+
__STL_TEMPLATE_NULL struct hash<unsigned short> {
75+
size_t operator()(unsigned short __x) const { return __x; }
76+
};
77+
__STL_TEMPLATE_NULL struct hash<int> {
78+
size_t operator()(int __x) const { return __x; }
79+
};
80+
__STL_TEMPLATE_NULL struct hash<unsigned int> {
81+
size_t operator()(unsigned int __x) const { return __x; }
82+
};
83+
__STL_TEMPLATE_NULL struct hash<long> {
84+
size_t operator()(long __x) const { return __x; }
85+
};
86+
__STL_TEMPLATE_NULL struct hash<unsigned long> {
87+
size_t operator()(unsigned long __x) const { return __x; }
88+
};
89+
90+
__STL_END_NAMESPACE
91+
92+
#endif /* __SGI_STL_HASH_FUN_H */
93+
94+
// Local Variables:
95+
// mode:C++
96+
// End:
Lines changed: 82 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,82 @@
1+
// file: 5hashtable-test.cpp
2+
3+
// #include <hash_set> // for hashtable
4+
#include <backward/hashtable.h> // for hashtable in mingw c++
5+
#include <iostream>
6+
7+
using namespace std;
8+
9+
int main() {
10+
// hash-table
11+
// <value, key, hash-func, extract-key, equal-key, allocator>
12+
// note: hash-table has no default ctor
13+
14+
__gnu_cxx::hashtable<int,
15+
int,
16+
hash<int>,
17+
_Identity<int>,
18+
equal_to<int>,
19+
allocator<int>>
20+
iht(50, hash<int>(), equal_to<int>()); // 指定50个buckets与函数对象
21+
22+
cout << iht.size() << endl;
23+
cout << iht.bucket_count() << endl; // 第一个质数
24+
cout << iht.max_bucket_count() << endl; // 最后一个质数
25+
26+
iht.insert_unique(59);
27+
iht.insert_unique(63);
28+
iht.insert_unique(108);
29+
iht.insert_unique(2);
30+
iht.insert_unique(53);
31+
iht.insert_unique(55);
32+
cout << iht.size() << endl;
33+
34+
// 声明hashtable迭代器
35+
// __gnu_cxx::hashtable<int,
36+
// int,
37+
// hash<int>,
38+
// _Identity<int>,
39+
// equal_to<int>,
40+
// allocator<int>>
41+
// ::iterator ite = iht.begin();
42+
// 使用auto可以避免上述长串,注意auto做函数返回类型时不会是引用
43+
auto ite = iht.begin();
44+
45+
// 使用迭代器遍历hashtable输出所有节点值
46+
for (int i = 0; i < iht.size(); ++i, ++ite)
47+
cout << *ite << ' ';
48+
cout << endl;
49+
50+
// 遍历所有buckets,如果节点个数不为0则打印
51+
for (int i = 0; i < iht.bucket_count(); ++i) {
52+
int n = iht.elems_in_bucket(i);
53+
if (n!=0)
54+
cout << "bucket[" << i << "] has " << n << " elems." << endl;
55+
}
56+
57+
// 验证bucket(list)的容量就是buckets vector的大小
58+
for (int i = 0; i <= 47; ++i) {
59+
iht.insert_equal(i);
60+
}
61+
cout << iht.size() << endl;
62+
cout << iht.bucket_count() << endl;
63+
64+
// 遍历所有buckets,如果节点个数不为0则打印
65+
for (int i = 0; i < iht.bucket_count(); ++i) {
66+
int n = iht.elems_in_bucket(i);
67+
if (n!=0)
68+
cout << "bucket[" << i << "] has " << n << " elems." << endl;
69+
}
70+
71+
// 使用迭代器遍历hashtable输出所有节点值
72+
ite = iht.begin();
73+
for (int i = 0; i < iht.size(); ++i, ++ite)
74+
cout << *ite << ' ';
75+
cout << endl;
76+
77+
cout << *(iht.find(2)) << endl;
78+
cout << iht.count(2) << endl;
79+
80+
// template argument deduction/substitution failed
81+
// iht.insert_unique(string("jjhou"));
82+
}
Lines changed: 70 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,70 @@
1+
// file: 5hashset-test.cpp
2+
3+
#include <iostream>
4+
#include <hash_set>
5+
#include <cstring>
6+
7+
using namespace std;
8+
9+
// 仿函数
10+
struct eqstr {
11+
bool operator() (const char* s1, const char* s2) const {
12+
return strcmp(s1, s2) == 0;
13+
}
14+
};
15+
16+
void lookup(const __gnu_cxx::hash_set<const char*, hash<const char*>, eqstr>& Set,
17+
const char* word) {
18+
__gnu_cxx::hash_set<const char *, hash<const char *>, eqstr>::const_iterator it = Set.find(word);
19+
cout << " " << word << ": " << (it != Set.end() ? "present" : "not present") << endl;
20+
}
21+
22+
int main() {
23+
__gnu_cxx::hash_set<const char *, hash<const char *>, eqstr> Set;
24+
Set.insert("kiwi");
25+
Set.insert("plum");
26+
Set.insert("apple");
27+
Set.insert("mango");
28+
Set.insert("apricot");
29+
Set.insert("banana");
30+
31+
lookup(Set, "mango");
32+
lookup(Set, "apple");
33+
lookup(Set, "durian");
34+
35+
auto ite1 = Set.begin();
36+
auto ite2 = Set.end();
37+
38+
for (; ite1 != ite2; ++ite1)
39+
cout << *ite1 << ' ';
40+
cout << endl;
41+
42+
__gnu_cxx::hash_set<int> iSet;
43+
iSet.insert(59);
44+
iSet.insert(63);
45+
iSet.insert(108);
46+
iSet.insert(2);
47+
iSet.insert(53);
48+
iSet.insert(55);
49+
50+
auto ite11 = iSet.begin();
51+
auto ite22 = iSet.end();
52+
// 为何已排序:
53+
// 因为bucket为193(内置28个质数中大于100的最小质数)
54+
// bucket足够多,造成排序假象
55+
for (; ite11 != ite22; ++ite11)
56+
cout << *ite11 << ' ';
57+
cout << endl;
58+
59+
iSet.clear();
60+
iSet.insert(3);
61+
iSet.insert(196);
62+
iSet.insert(1);
63+
iSet.insert(389);
64+
iSet.insert(194);
65+
iSet.insert(387);
66+
ite11 = iSet.begin();
67+
for (; ite11 != ite22; ++ite11)
68+
cout << *ite11 << ' ';
69+
cout << endl;
70+
}

0 commit comments

Comments
 (0)