帕斯卡尔的零指针

时间:2013-05-25 11:35:10

标签: pointers pascal behavior

我在解决Pascal中设置为nil的指针的行为时遇到问题。我正在使用turbo pascal 7.0。 似乎当我设置两个指针时,尾部为零......它们似乎总是指向未来相同的值,即使它们被分配给不同值。

在下面的代码中,当我注释掉问题区域并获得预期结果时。

当我从这对行中删除评论时 头:=零; 尾:=无;

'head'指针在取消引用时似乎始终采用赋予'tail'指针的值。任何见解将不胜感激。

    program LinkedListTest;
type
    ListNodePtr = ^ListNode;
    ListNode = record
        key,cycleLength: integer;
        NodePtr: ListNodePtr;
    end;

{
We have just defined the node of a linked list.
Next we declare our head which is the pointer to the first node
and the tail which points to the last node.
The head helps us find our first node in the list
the tail helps us to keep track of the last node in the list.
Both are simple pointers to a node (in our case ListNodePtr).
}

var
head,tail : ListNodePtr;
node1,node2,node3,node4: ListNode;
count: integer;

{Init the linked list}

procedure InitLinkedList;
Begin
new(head);
new(tail);

(*   **Remove comments from this code to see problems in final output**
head:=nil;
tail:=nil;
*)
node1.key:=10;

new(node1.NodePtr);
node1.NodePtr:=nil;
head^:=node1;
tail^:=node1;
writeln('head key is now: ',head^.key);



node2.key:=20;
new(node2.NodePtr);
node2.NodePtr:=nil;




head^.NodePtr^:=node2;



tail^:=node2;

writeln('head key is now: ',head^.key);
writeln('tail key is now: ',tail^.key);
writeln('node1 key is now: ',node1.key);
writeln('node2 key is now: ',node2.key);
readln;
end;

begin

InitLinkedList;

end
.

2 个答案:

答案 0 :(得分:1)

有几件奇怪的事情。

您加载数据以在堆栈(node1)上分配记录,该记录将在过程退出时消失,然后将其内容(不是引用/指针)深度复制到分配给head和tail的记录中(使用new)。

       head^:=node1;
       tail^:=node1;

此时,您有三个node1的内容副本,node1,head ^和tail ^

使用node2会犯同样的错误。 (head ^ .NodePtr ^:= node2)

您可以通过简单地指定点来分配点,例如

     head:=tail;

并直接访问字段

       head^.field:=something

如果头指向理智的东西。

这个结构:

  new(node1.NodePtr);
  node1.NodePtr:=nil;

本质上是内存泄漏。您将记录的空间分配给nodeptr,但随后立即为其分配NIL,不会引用刚刚分配的记录。

提示:首先用纸箱(表示记录)和箭头(表示指针)在纸上计算出你的算法。

答案 1 :(得分:1)

修订版1-删除了局部变量Node1和Node2

将tail'next node'指针设置为nil

检查头部是否指向列表中2个节点的尾部

基于答案的更新解决方案

program LinkedListTest;
type
    ListNodePtr = ^ListNode;
    ListNode = record
        key,cycleLength: integer;
        NodePtr: ListNodePtr;
    end;


var
head,tail,tempPtr : ListNodePtr;
count: integer;
pointerIsNil: boolean;
{Init the linked list}


begin

new(head);
new(tail);
new(tempPtr);
tempPtr^.key:=10;
head:=tempPtr;
tail:=tempPtr;
tail^.NodePtr:=nil;
writeln('head key is now: ',head^.key);
writeln('tail key is now: ',tail^.key);
pointerIsNil:=head^.NodePtr = nil;
writeln('Is heads node ptr nil? Answer is: ',pointerIsNil);
new(tempPtr);
tempPtr^.key:=20;
head^.Nodeptr:=tempPtr;
tail:=tempPtr;
writeln('head key is now: ',head^.key);
writeln('tail key is now: ',tail^.key);

pointerIsNil:=head^.NodePtr = nil;
writeln('Is heads node ptr nil? Answer is: ',pointerIsNil);
writeln('Making sure head is linked to the tail ',head^.NodePtr^.key);


readln;


end
.