mirror of
https://github.com/Nekrolm/ubbook.git
synced 2025-12-18 13:14:41 +03:00
overflow in hash
This commit is contained in:
@@ -31,7 +31,21 @@ if (x > 0 && a > 0 && x + a <= 0) {
|
|||||||
|
|
||||||
Но, увы, это неопреденной поведение. И компилятор имеет полное право [выкинуть](https://godbolt.org/z/dhs83T) такую проверку.
|
Но, увы, это неопреденной поведение. И компилятор имеет полное право [выкинуть](https://godbolt.org/z/dhs83T) такую проверку.
|
||||||
|
|
||||||
Корректные проверки куда сложнее и тяжелее.
|
Искусственный пример может быть недостаточно убедительным, так что обратим внимание на следущую, вполне серьезную, функцию вычисления полиномиального хэша строки:
|
||||||
|
```C++
|
||||||
|
int hash_code(std::string s) {
|
||||||
|
int h = 13;
|
||||||
|
for (char c : s) {
|
||||||
|
h += h * 27752 + c;
|
||||||
|
}
|
||||||
|
if (h < 0) h += std::numeric_limits<int>::max();
|
||||||
|
return h;
|
||||||
|
}
|
||||||
|
```
|
||||||
|
Функция, которая никогда не должна, по задумке, возвращать отрицательные числа, таки [выдает](https://godbolt.org/z/4v139E) отрицательное число! Из-за неопределенного поведения и бессмысленной с точки зрения компилятора проверки.
|
||||||
|
|
||||||
|
|
||||||
|
Корректные проверки переполнения куда сложнее и тяжелее.
|
||||||
|
|
||||||
Так, для C++20, безопасный обобщенный код арифметических операций над целыми знаковыми числами мог бы выглядеть так
|
Так, для C++20, безопасный обобщенный код арифметических операций над целыми знаковыми числами мог бы выглядеть так
|
||||||
|
|
||||||
@@ -199,3 +213,4 @@ x *= x; // переписывается как x = x * x;
|
|||||||
### Полезные ссылки
|
### Полезные ссылки
|
||||||
1. https://wiki.sei.cmu.edu/confluence/display/c/INT32-C.+Ensure+that+operations+on+signed+integers+do+not+result+in+overflow
|
1. https://wiki.sei.cmu.edu/confluence/display/c/INT32-C.+Ensure+that+operations+on+signed+integers+do+not+result+in+overflow
|
||||||
2. https://stackoverflow.com/a/46073296
|
2. https://stackoverflow.com/a/46073296
|
||||||
|
3. https://habr.com/ru/post/307702/
|
||||||
|
|||||||
Reference in New Issue
Block a user