简体   繁体   English

为什么我的指针改变一个固定的数字?

[英]Why does my pointer change by a fixed number?

I have defined my own type. 我已经定义了自己的类型。 It contains a pointer to an array, as well as how many items are in that array 它包含一个指向数组的指针,以及该数组中有多少项

struct neighborList
{
    unsigned int nNeighbors;
    unsigned int* pNeighbors; 
};

These get instantiated, populated, and eventually I want to go back through them. 这些实例化,填充,最后我想回顾它们。 Then something very strange happens. 然后发生非常奇怪的事情。 I think screenshots are better than words here. 我认为屏幕截图比这里的文字更好。

在此处输入图片说明

I've shown the next statement to execute. 我已经显示了要执行的下一条语句。 I have an array of the aforementioned data type, and the one under consideration here has 1 neighbor and the address of that 1 neighbor is 0x107a28; 我有一个上述数据类型的数组,这里考虑的一个有1个邻居,那个1个邻居的地址是0x107a28; Cool. 凉。 But what actually gets assigned to pLook? 但是实际上分配给pLook的是什么?

在此处输入图片说明

The address is always off by 0x40. 地址始终关闭0x40。 Has anyone seen anything like this? 有人看到过这样的东西吗? Help here is appreciated. 感谢您的帮助。

EDIT: Here's the whole thing since several people want to see it. 编辑:这是整个过程,因为有几个人希望看到它。

#include "stdafx.h"
#include <stdlib.h>
#include <time.h>

//#define NVERTEX 875714
#define NVERTEX 9

struct linkedNode
{
    unsigned int node;
    linkedNode* pNextLinkedNode;
    linkedNode* pPrevLinkedNode; 
};

struct neighborList
{
    unsigned int nNeighbors;
    unsigned int* pNeighbors; 
};

struct linkedNodeList
{
    linkedNode* pHead;
    linkedNode* pTail;
};

void populateNeighbors(neighborList* pNeighborList, FILE* fp);
void DFSLoop(neighborList* pNeighborList, linkedNode* pOutput, unsigned int nNodes); 
void append(linkedNodeList* pLinkedList, unsigned int node);

void DFSLoop(neighborList* pNeighborList, linkedNodeList* pOutput, unsigned int nNodes)
{
    bool* visitedArray;
    bool* cashedArray;
    unsigned int* leaderArray;
    unsigned int* finishingTimes;
    unsigned int t = 0; 

    visitedArray = (bool*)malloc(nNodes*sizeof(bool));
    cashedArray = (bool*)malloc(nNodes*sizeof(bool)); 
    leaderArray = (unsigned int*)malloc(nNodes*sizeof(unsigned int)); 
    finishingTimes = (unsigned int*)malloc(nNodes*sizeof(unsigned int)); 

    //initialize all arrays to all false/0
    for (unsigned int i = 0; i < nNodes; i++)
    {
        visitedArray[i] = false;
        cashedArray[i] = false; 
        leaderArray[i] = 0;
        finishingTimes[i] = 0;
    }

    //firstly, pick a starting node and put it on the linkedList
    //initialize head and tail
    (pOutput->pHead)->node = 1;
    (pOutput->pHead)->pNextLinkedNode = NULL;
    (pOutput->pHead)->pPrevLinkedNode = NULL;

    (pOutput->pTail)->node = 1;
    (pOutput->pTail)->pNextLinkedNode = NULL;
    (pOutput->pTail)->pPrevLinkedNode = NULL;

    unsigned int curNode = (pOutput->pTail)->node;
    for (;;)
    {
        //Start DFS
        //#1 If current node under consideration has an unexplored neighbor, make it the new tail and repeat
        //   If not, current node is cashed. Set it's finishing time, and leader. Work back through the list
        //   Until you find a node with an unexplored neighbor
        unsigned int nNeighbors = pNeighborList[curNode].nNeighbors;

        for (unsigned int i = 0; i < nNeighbors; i++)
        {
            unsigned int* pLook = (pNeighborList[curNode]).pNeighbors;
            unsigned int neighbor = pLook[0];
            /*
            unsigned int nodeUnderConsideration = (pNeighborList[curNode].pNeighbors)[i];

            if ( !cashedArray[nodeUnderConsideration])
            {
                append(pOutput, (pNeighborList[curNode].pNeighbors)[i]); 
                curNode = (pOutput->pTail)->node;
                continue; 
            }
            */
        }


        //#2 If you make it back to the head and have no unexplored neighbors, pick new vertex (if unvisited) and repeat



    }


    free(visitedArray);
    free(cashedArray); 
    free(leaderArray);
    free(finishingTimes); 
}

int _tmain(int argc, _TCHAR* argv[])
{
    //open file
    FILE* fp;
    FILE* fpRev;
    //fp = fopen("SCC.txt", "rb"); 
    //fpRev = fopen("SSCrev.txt", "rb"); 
    fp = fopen("SSCsmall1.txt", "rb"); 
    fpRev = fopen("SSCsmall1rev.txt", "rb");

    /* read file. When reading, keep track of how much memory to malloc */
    /* for each vertex */
    neighborList* pAllEdges;
    neighborList* pAllEdgesRev;
    pAllEdges = (neighborList*)malloc(NVERTEX*sizeof(neighborList)); 
    pAllEdgesRev = (neighborList*)malloc(NVERTEX*sizeof(neighborList)); 

    populateNeighbors(pAllEdges, fp);
    populateNeighbors(pAllEdgesRev, fpRev); 

    //instantiate pointers for linkedlists needed for DFS
    linkedNodeList NodesFirstPass, NodesSecondPass;
    NodesFirstPass.pHead = (linkedNode*)malloc(sizeof(linkedNode)); 
    NodesFirstPass.pTail = NodesFirstPass.pHead; 
    NodesSecondPass.pHead = (linkedNode*)malloc(sizeof(linkedNode)); 
    NodesSecondPass.pTail = NodesSecondPass.pHead; 

    DFSLoop(pAllEdges, &NodesFirstPass, NVERTEX); 

    free(pAllEdges); 
    free(pAllEdgesRev); 
    return 0;
}

void populateNeighbors(neighborList* pNeighborList, FILE* fp)
{
    unsigned int v1 = 1;
    unsigned int v2 = 1;

    unsigned int v1_next = 1;
    unsigned int v2_next = 1; 
    unsigned int neighbors [1000]; 
    fscanf(fp, "%u", &v1_next); 
    fscanf(fp, "%u", &v2_next); 

    for (unsigned int i = 0; i < (NVERTEX - 1); i++)
    {
        //initialize nNeigbors to 0
        unsigned int nNeighbors = 0;

        for (;;)
        {
            //if v1_next is a different vertex then v1, then copy v1_next to v1, 
            //malloc what we need to, copy over the array and continue
            if (v1_next != v1)
            {
                pNeighborList[i].nNeighbors = nNeighbors; 

                if (nNeighbors != 0) 
                {
                    pNeighborList[i].pNeighbors = (unsigned int*)malloc(nNeighbors * sizeof(unsigned int));

                    for (unsigned int j = 0; j < nNeighbors; j++)
                    {
                        pNeighborList[i].pNeighbors[j] = neighbors[j]; 
                    }

                }

                v1++;
                break;
            }

            //else, increment the neighbor count for this particular vertex and continue
            //within this loop, getting new neighbors (edges)
            else
            {
                neighbors[nNeighbors] = v2_next; 
                nNeighbors++;
                if (nNeighbors == 1000) 
                {
                    break; 
                }
                fscanf(fp, "%u", &v1_next);
                fscanf(fp, "%u", &v2_next); 
            }
        }
    }

}

void append(linkedNodeList* pLinkedList, unsigned int node)
{
    //make new node with the intention that it's going to be the new tail
    linkedNode* pNewNode = (linkedNode*)malloc(sizeof(linkedNode));
    pNewNode->node = node; 
    pNewNode->pNextLinkedNode = NULL;
    pNewNode->pPrevLinkedNode = pLinkedList->pTail;

    //set next node of current tail to new node
    (pLinkedList->pTail)->pNextLinkedNode = pNewNode; 

    //new tail becomes new node
    pLinkedList->pTail = pNewNode; 

    //lastly, set old tail's next node to point to new tail
    (pLinkedList->pTail->pPrevLinkedNode)->pNextLinkedNode = pLinkedList->pTail;
}

Judging by the screenshots, and assuming you are on a 64 bit system (a pointer being 8 bytes wide), the pointer pNeighborList links to the start of the list, while pLook links to the pNeighbors attribute of a neighborList element at index 5 : 从屏幕快照来看,并假设您使用的是64位系统(指针为8字节宽),指针pNeighborList链接到列表的开头 ,而pLook链接到索引5neighborList元素的pNeighbors属性:

// assuming sizeof(neighborList) == 4 (int) + 8 (pointer) = 12 bytes

neighborList* pNeighborList = new neighborList[10];
// pNeighborList points to the start of the list, 0x00107a28

// pNeighborList[5] is at address 0x00107a64 (start + 5 * sizeof(neighborList)
// .pNeighbors is offset 4 more bytes (sizeof(unsigned int)) = 0x00107a68

int curNode = 5;
unsigned int* pLook = (pNeighborList[curNode]).pNeighbors;
// pLook points to pNeighbors of the element at index 5, 0x00107a68

When you hover the pointer pNeighborList in Visual Studio, it shows you the pointer (which points to the start of the list), not the full value ( (pNeighborList[curNode]).pNeighbors ). 当您将指针pNeighborList在Visual Studio中的指针pNeighborList时,它将显示指针(指向列表的开头),而不是完整值( (pNeighborList[curNode]).pNeighbors )。

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

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