简体   繁体   English

优先队列的这部分C代码如何工作?

[英]How does this segment of C code for a priority queue work?

I'm a bit overwhelmed at this line specifically: 我对这条线有些不知所措:

 Entry** newHeap = (Entry**)malloc(sizeof(Entry*) * newHeapLength);

in this code: 在此代码中:

 /**
     * Expands the heap array of the given priority queue by 
     *   replacing it with another that is double its size.
     *
     * @param  pq  the priority queue whose heap is to be doubled in size
     * return  1 for successful expansion or an error code:
     */
    int expandHeap (PriorityQueue *pq)
    {
        int returnCode = 1;
        int newHeapLength = pq->heapLength * 2;
        Entry** newHeap = (Entry**)malloc(sizeof(Entry*) * newHeapLength);
        if (newHeap != NULL) 
        {
            int index;
            for (index = 0; index < pq->heapLength; index++) 
            {
                newHeap[index] = pq->heap[index];
            }
            free(pq->heap);
            pq->heap = newHeap;
            pq->heapLength = newHeapLength;
        }
        else
        {
            returnCode = -1;  // TODO: make meaningful error codes
        }
        return returnCode;
    }
Entry** newHeap = (Entry**)malloc(sizeof(Entry*) * newHeapLength);
      |                      |
newHeap is a             malloc allocates a chunk in memory that is the size of 
pointer to a             a pointer to an Entry times newHeapLength
pointer to an Entry

It just allocates an array for you, at run-time. 它只是在运行时为您分配一个数组。 Usually the size of array must be specified at compile-time. 通常,数组的大小必须在编译时指定。 But here it is specified at run-time, it's newHeapLength . 但是这里是在运行时指定的,它是newHeapLength Each entry ("cell") in that array must be capable of storing a value of type Entry* in it. 该数组中的每个条目(“单元格”)必须能够在其中存储Entry*类型的值。 In C, arrays are contiguous, so the total size of the array, in bytes, is just a product of the two numbers: sizeof(Entry*) * newHeapLength . 在C中,数组是连续的,因此数组的总大小(以字节为单位)只是两个数字的乘积: sizeof(Entry*) * newHeapLength Now newHeap can be used to address this array in a usual manner: eg newHeap[8] . 现在,可以使用newHeap以通常的方式来寻址此数组:例如newHeap[8] Of course, if 8 >= newHeapLength , this would be accessing past the allocated area, which is bad . 当然,如果8 >= newHeapLength ,这将是访问分配的区域,这是不好的

For array storing 10 int s, int ia[10]; 对于存储10个int的数组, int ia[10]; , the type of ia is int * ( correction: almost. but we can pretend that it is, for the purposes of this explanation ). ia的类型为int *更正:几乎。但是,出于解释的目的,我们可以假装为 )。 Here, similarly, for array storing values of type Entry* , the type is (Entry*)* . 在这里,类似地,对于存储类型为Entry*值的数组,类型为(Entry*)* Simple. 简单。 :) :)

And of course you must cast the return value of malloc to your type, to be able to address that array with it. 当然,您必须将malloc的返回值转换为您的类型,以便能够使用该地址寻址该数组。 malloc by itself returns an address as void* . malloc本身返回一个地址为void* Meaning. 含义。 the size of memory cell which it points to, is proclaimed unknown . 它所指向的存储单元的大小被称为未知 When we say that ia is of type int* , what we actually saying is that memory cell pointed to by it has size of sizeof(int) . 当我们说ia的类型为int* ,实际上是说它所指向的存储单元的大小为sizeof(int) So when we write ia[3] , it is actually translated into *(ia+3) which is actually *(int*)(void*)( (unsigned int)(void*)ia + 3*sizeof(int) ) . 因此,当我们编写ia[3] ,它实际上被转换为*(ia+3) ,实际上是*(int*)(void*)( (unsigned int)(void*)ia + 3*sizeof(int) ) In other words, the compiler just adds sizeof(int) three times to the starting address, thus "hopping over" three sizeof(int) -wide cells of memory. 换句话说,编译器仅将sizeof(int)添加到起始地址三倍,从而“跳过”三个sizeof(int)宽的内存单元。 And for newHeap[8] it will just "hop" over 8 sizeof(Entry*) -wide memory cells, to get the address of the 9-th entry in that array (counting from 1). 对于newHeap[8] ,它将仅“跳”过8个sizeof(Entry*)宽的存储单元,以获取该数组中第9个条目的地址(从1开始计数)。

Also, see hashed array tree for an alternative to the geometric expansion, which is what that code is doing. 另外,请参见哈希数组树 ,以了解几何扩展的替代方法,即代码正在执行的操作。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM