Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

堆定时器数组溢出问题 #101

Open
ad1510875353 opened this issue Mar 9, 2024 · 7 comments
Open

堆定时器数组溢出问题 #101

ad1510875353 opened this issue Mar 9, 2024 · 7 comments

Comments

@ad1510875353
Copy link

在原先的堆上滤的函数中,由于i是无符号数,因此会将与其进行运算的数全部转为无符号数,包括结果,因此当i==0时,i-1的结果是一个很大的整数,从而导致j超过了vector的size,从而导致了溢出。因此可以改成以下形式。

void HeapTimer::siftup_(size_t i)
{
assert(i >= 0 && i < heap_.size());
size_t j = (i - 1) / 2;
while (j >= 0 && i > 0 && heap_[j] < heap_[i])
{
SwapNode_(i, j);
i = j;
j = (i - 1) / 2;
}
}

另外,作者代码里使用了大量assert来方便调试,但是实际使用时这些判断会影响服务器性能,因此性能测试时构建release版本,可以提高服务器性能。

@1900100209
Copy link

在原先的堆上滤的函数中,由于i是无符号数,因此会将与其进行运算的数全部转为无符号数,包括结果,因此当i==0时,i-1的结果是一个很大的整数,从而导致j超过了vector的size,从而导致了溢出。因此可以改成以下形式。

void HeapTimer::siftup_(size_t i) { assert(i >= 0 && i < heap_.size()); size_t j = (i - 1) / 2; while (j >= 0 && i > 0 && heap_[j] < heap_[i]) { SwapNode_(i, j); i = j; j = (i - 1) / 2; } }

另外,作者代码里使用了大量assert来方便调试,但是实际使用时这些判断会影响服务器性能,因此性能测试时构建release版本,可以提高服务器性能。

当插入第一个元素(i为0)的时候,不应该考虑上滤

@1900100209
Copy link

在原先的堆上滤的函数中,由于i是无符号数,因此会将与其进行运算的数全部转为无符号数,包括结果,因此当i==0时,i-1的结果是一个很大的整数,从而导致j超过了vector的size,从而导致了溢出。因此可以改成以下形式。

void HeapTimer::siftup_(size_t i) { assert(i >= 0 && i < heap_.size()); size_t j = (i - 1) / 2; while (j >= 0 && i > 0 && heap_[j] < heap_[i]) { SwapNode_(i, j); i = j; j = (i - 1) / 2; } }

另外,作者代码里使用了大量assert来方便调试,但是实际使用时这些判断会影响服务器性能,因此性能测试时构建release版本,可以提高服务器性能。

我怎么感觉他做的这个是最大堆呢,父节点比子节点大

@peng-yq
Copy link

peng-yq commented May 8, 2024

在原先的堆上滤的函数中,由于i是无符号数,因此会将与其进行运算的数全部转为无符号数,包括结果,因此当i==0时,i-1的结果是一个很大的整数,从而导致j超过了vector的size,从而导致了溢出。因此可以改成以下形式。

void HeapTimer::siftup_(size_t i) { assert(i >= 0 && i < heap_.size()); size_t j = (i - 1) / 2; while (j >= 0 && i > 0 && heap_[j] < heap_[i]) { SwapNode_(i, j); i = j; j = (i - 1) / 2; } }

另外,作者代码里使用了大量assert来方便调试,但是实际使用时这些判断会影响服务器性能,因此性能测试时构建release版本,可以提高服务器性能。

确实,这里需要修改一下

@peng-yq
Copy link

peng-yq commented May 8, 2024

在原先的堆上滤的函数中,由于i是无符号数,因此会将与其进行运算的数全部转为无符号数,包括结果,因此当i==0时,i-1的结果是一个很大的整数,从而导致j超过了vector的size,从而导致了溢出。因此可以改成以下形式。
void HeapTimer::siftup_(size_t i) { assert(i >= 0 && i < heap_.size()); size_t j = (i - 1) / 2; while (j >= 0 && i > 0 && heap_[j] < heap_[i]) { SwapNode_(i, j); i = j; j = (i - 1) / 2; } }
另外,作者代码里使用了大量assert来方便调试,但是实际使用时这些判断会影响服务器性能,因此性能测试时构建release版本,可以提高服务器性能。

我怎么感觉他做的这个是最大堆呢,父节点比子节点大

父节点比子节点大是最小堆的意思,堆顶是最小的,老哥复习一下数据结构

@1900100209
Copy link

在原先的堆上滤的函数中,由于i是无符号数,因此会将与其进行运算的数全部转为无符号数,包括结果,因此当i==0时,i-1的结果是一个很大的整数,从而导致j超过了vector的size,从而导致了溢出。因此可以改成以下形式。
void HeapTimer::siftup_(size_t i) { assert(i >= 0 && i < heap_.size()); size_t j = (i - 1) / 2; while (j >= 0 && i > 0 && heap_[j] < heap_[i]) { SwapNode_(i, j); i = j; j = (i - 1) / 2; } }
另外,作者代码里使用了大量assert来方便调试,但是实际使用时这些判断会影响服务器性能,因此性能测试时构建release版本,可以提高服务器性能。

我怎么感觉他做的这个是最大堆呢,父节点比子节点大

父节点比子节点大是最小堆的意思,堆顶是最小的,老哥复习一下数据结构

要不你再查查?最大堆是父节点比子节点大

@peng-yq
Copy link

peng-yq commented May 8, 2024

在原先的堆上滤的函数中,由于i是无符号数,因此会将与其进行运算的数全部转为无符号数,包括结果,因此当i==0时,i-1的结果是一个很大的整数,从而导致j超过了vector的size,从而导致了溢出。因此可以改成以下形式。
void HeapTimer::siftup_(size_t i) { assert(i >= 0 && i < heap_.size()); size_t j = (i - 1) / 2; while (j >= 0 && i > 0 && heap_[j] < heap_[i]) { SwapNode_(i, j); i = j; j = (i - 1) / 2; } }
另外,作者代码里使用了大量assert来方便调试,但是实际使用时这些判断会影响服务器性能,因此性能测试时构建release版本,可以提高服务器性能。

我怎么感觉他做的这个是最大堆呢,父节点比子节点大

父节点比子节点大是最小堆的意思,堆顶是最小的,老哥复习一下数据结构

要不你再查查?最大堆是父节点比子节点大

不好意思打错字了...,原作者实现的是小顶堆:

size_t j = (i - 1) / 2;
if (heap_[j] < heap_[i]) {
    break;
}

j是父节点的索引,只要父节点的值大于子节点就进行交换,否则跳出循环,也就是用vector模拟小顶堆。

@peng-yq
Copy link

peng-yq commented May 8, 2024

在原先的堆上滤的函数中,由于i是无符号数,因此会将与其进行运算的数全部转为无符号数,包括结果,因此当i==0时,i-1的结果是一个很大的整数,从而导致j超过了vector的size,从而导致了溢出。因此可以改成以下形式。

void HeapTimer::siftup_(size_t i) { assert(i >= 0 && i < heap_.size()); size_t j = (i - 1) / 2; while (j >= 0 && i > 0 && heap_[j] < heap_[i]) { SwapNode_(i, j); i = j; j = (i - 1) / 2; } }

另外,作者代码里使用了大量assert来方便调试,但是实际使用时这些判断会影响服务器性能,因此性能测试时构建release版本,可以提高服务器性能。

另外在GetNextTick中也有一个同样的小问题,作者直接令size_t res = -1,size_t 是无符号类型,如果尝试将 -1 赋值给它,会得到一个非常大的数

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

3 participants