最近,在我当前项目中读取前代码时,我遇到了以下问题:
在实现Queue时,我的前代写了这样的代码:
while(uq->pHead)
{
char *tmp = uq->pHead;
uq->pHead = *(char **)tmp;
//...
}
uq-> pHead的定义如下:
typedef struct {
char* pHead;
//...
} Queue;
好吧,我对“uq->pHead = *(char**)tmp
”的用法感到很困惑,有人能详细解释一下吗?
如果我们假设*(uq-> pHead)= 32(即''),*(char**)tmp
会将其转换为指针形式,但......它怎么会有意义呢?
非常感谢。
答案 0 :(得分:6)
我们假设我们将您的队列实现为链接列表。我们可能有:
struct data_type;
struct node
{
node *next;
data_type item;
};
struct linked_list
{
node *pHead;
// ...
};
要清空链表,我们可能会写:
linked_list *uq=...;
while (uq->pHead)
{
// unlink the first node from the list
node *tmp = uq->pHead;
uq->pHead = tmp->next;
// do something with that node
// ...
// deallocate the node
free(tmp);
}
现在假设我们并不真正关心可维护的代码,或者其他方面都是懒惰的。我们可能只是想象任何指针都会做,并将'node'的结构保留在我们的头脑中,然后写:
linked_list *uq=...;
while (uq->pHead)
{
// unlink the first node
char *tmp = uq -> pHead; // tmp points to the first 'node'
uq -> pHead = *(char**)tmp; // The first thing in a 'node' is a pointer to
// the next node.
// do something with 'tmp', the now unlinked node
data_type *item=(data_type*) ( ((char**)tmp) + 1 ); // after the 'next' pointer
// is the real data.
// ...
// free up the node
free(tmp);
}
答案 1 :(得分:2)
Queue
结构可能是......一个队列。并且它的第一个元素似乎是指向队列的下一个或上一个项目的指针。听起来编码器不能使用他正在创建的类型 - 队列 - 在队列本身内。
例如,解决方案是
typedef struct Queue {
struct Queue *pHead;
//...
} Queue;
回到你的问题,
char *tmp = uq->pHead;
将tmp
设置为当前的Queue项(保存以供以后使用)
uq->pHead = *(char **)tmp;
将uq->pHead
指针值设置为当前项的pHead。由于编码器未正确声明pHead(char *
而不是struct Queue *
),因此它将结构指针(uq->pHead
== tmp
)强制转换为char **
并且然后*(char **)
检索结构的第一个指针,即pHead
。
使用我的上述声明,代码可能是
while(uq->pHead)
{
Queue *tmp = uq->pHead;
uq->pHead = tmp->pHead; // or uq->pHead = uq->pHead->pHead
//...
}
答案 2 :(得分:2)
在这个队列中,pHead指向另一个pHead.More恰当地写成:
void *pHead;
tmp也可以写成:
void *tmp;
tmp = uq->pHead;
将当前的pHead指针保存到tmp变量
现在,tmp被转换为(void **)
,因此tmp被视为指向另一个指针
*(void **) tmp;
是tmp的值,也被视为指针。
uq->pHead = *(void **) tmp;
因此,这会将pHead增加到下一个元素 该声明也可以写成:
uq->pHead = uq->pHead->pHead;
对不起,如果我困惑你。
答案 3 :(得分:0)
假设您的Queue结构有一个名为qa的对象,qa的第一个数据的地址与qa的相同。在C ++中,您可以通过多种方式调用数据,例如“。”,“ - >” 。但它们都是真正使用偏移,就像
`#include<cstdio>
using namespace std;
class A
{
public:
int a;
int b;
};
int main()
{
A a;
printf("%p\n",&a);
printf("%p\n",& A::a);
printf("%p\n",& A::b);
printf("%p\n",&(a.a));
printf("%p\n",&(a.b));
return 0;
}`
您可以从此代码中获得所需内容。