[英]Why object's value changes even though it has different references?
I am confused about objects references here.我对这里的对象引用感到困惑。 It is LC problem to merge 2 sorted linked lists.
合并 2 个已排序的链表是 LC 问题。
I understand that at first iteration current.next
and result
have reference the same object so when i assign new value to current.next
the result
value changes as well.我知道在第一次迭代
current.next
和result
引用了同一个对象,所以当我为current.next
分配新值时, result
值也会改变。
At the second iteration both r1 and r2 are false so result, current and current.next
point to diffrent objects.在第二次迭代时,r1 和 r2 都是假的,因此
result, current and current.next
指向不同的对象。
What i don't understand is why assigning new value to current ( current = current.next
) doesn't modify result object but current.next = l1/l2
does?我不明白的是为什么将新值分配给 current (
current = current.next
) 不会修改结果对象但current.next = l1/l2
会?
Could someone explain it to me please?有人可以向我解释一下吗?
public static ListNode MergeTwoLists(ListNode l1, ListNode l2)
{
if (l1 == null) return l2;
if (l2 == null) return l1;
if (l2 == null && l1 == null) return null;
ListNode result = new ListNode(0);
ListNode current = result;
while (l1 != null && l2 != null)
{
var r1 = Object.ReferenceEquals(result, current);
var r2 = Object.ReferenceEquals(result, current.next);
if (l1.val < l2.val)
{
current.next = l1;
l1 = l1.next;
}
else
{
current.next = l2;
l2 = l2.next;
}
current = current.next;
}
// l1 is lognger than l2
if(l1 != null)
{
current.next = l1;
l1 = l1.next;
}
// l2 is lognger than l1
if (l2 != null)
{
current.next = l2;
l2 = l2.next;
}
return result.next;
}
public class ListNode
{
public int val;
public ListNode next;
public ListNode(int x = 0, ListNode next = null)
{
val = x;
next = null;
}
}
EDIT编辑
Let's say we have these:假设我们有这些:
Input: l1 = [1,2,4], l2 = [1,3,4] Output: [1,1,2,3,4,4]
1st iteration :第一次迭代:
r1 = true
, both result and current point to the same object. r1 = true
, result 和 current 都指向同一个对象。
r2 = false
l1.val == l2.val
so we execute l1.val == l2.val
所以我们执行
else
{
current.next = l2;
l2 = l2.next;
}
At this moment we have: result = [0,1,3,4]
, current = [0,1,3,4], l2 = [3,4]
此时我们有:
result = [0,1,3,4]
, current = [0,1,3,4], l2 = [3,4]
Next we execute current = current.next
, so current = [1,3,4]
and it doesn't point to result anymore.接下来我们执行
current = current.next
,所以current = [1,3,4]
并且它不再指向 result 。
2nd iteration第二次迭代
r1 = false
, both result and current point to the different object. r1 = false
, result 和 current 都指向不同的对象。
r2 = false
, r2 = false
,
l1.val < l2.val
so we execute l1.val < l2.val
所以我们执行
if (l1.val < l2.val)
{
current.next = l1;
l1 = l1.next;
}
At this moment we have:此刻我们有:
result = [0,1,1,2,4], current = [1,1,2,4], l2 = [3,4], l1 = [2,4]
Here is the part i don't understand : Result and current point to diffrent objects, still when current changes result does as well.这是我不明白的部分:结果和当前指向不同的对象,当当前更改结果时仍然如此。 How result keeps reference to current??
结果如何保持对当前的引用?
Next we execute current = current.next
, so current = [1,2,4]
, so we modify current but this time result doesn't change.接下来我们执行
current = current.next
,所以current = [1,2,4]
,所以我们修改 current 但这次结果没有改变。
Result and current point to diffrent objects, still when current changes result does as well.
结果和当前指向不同的对象,当当前更改结果时仍然如此。 How result keeps reference to current?
结果如何保持对当前的引用?
Look at this part of your question:看看你问题的这一部分:
so
current = [1,3,4]
and it doesn't point to result anymore.所以
current = [1,3,4]
它不再指向结果。
Importantly, the 1
in that list is the same element as the 1
in result = [0,1,3,4]
.重要的是,
1
在该列表是作为相同的元件1
中result = [0,1,3,4]
If you modify the next
field of that 1
node, you will modify any list that node is a member of.如果您修改该
1
节点的next
字段,您将修改该节点所属的任何列表。 Including the list that result
is referencing.包括
result
引用的列表。
Later when you write:后来当你写:
At this moment we have:
此刻我们有:
result = [0,1,1,2,4], current = [1,1,2,4], l2 = [3,4], l1 = [2,4]
Note that the list result
points to is not the same as the list current
points to.请注意,该列表
result
点是不一样的列表current
点。 But after that first node, it is the same.但是在第一个节点之后,它是相同的。
After the first iteration, result.next
references the same object that current
does.在第一次迭代之后,
result.next
引用与current
相同的对象。 This is because result
and current
started at referencing the same object, and then as the last step of the first iteration, current
was changed to reference current.next
.这是因为
result
和current
从引用同一个对象开始,然后作为第一次迭代的最后一步, current
更改为引用current.next
。 Since current
and result
were at that point the same, current.next
and result.next
are also the same.由于
current
和result
在这一点上相同,因此current.next
和result.next
也相同。 So after changing current
to current.next
, that's the same as setting it to result.next
.因此,将
current
更改为current.next
,这与将其设置为result.next
相同。
So on the second iteration, result.next
and current
are the same.所以在第二次迭代中,
result.next
和current
是一样的。 This means that when you modify current.next
, that's the same as modifying result.next.next
, which has the effect of replacing the contents of the result
list beyond the first two elements, with the new chain of elements that l2
referenced.这意味着,当您修改
current.next
,这与修改result.next.next
相同,这具有将result
列表中除前两个元素之外的内容替换为l2
引用的新元素链的效果。
Again: the key here is that each variable simply points to a single node.再说一遍:这里的关键是每个变量都指向一个节点。 It's fine to conceptualize that as pointing to a list of nodes, but only if you remember that if you modify the
next
field of any node in that list, you are modifying the entire list, even if the variable is not referencing the variable that references the root of the list.可以将其概念化为指向节点列表,但前提是您记住,如果您修改该列表中任何节点的
next
字段,则您正在修改整个列表,即使该变量未引用引用的变量列表的根。
You should never assign current.next
to nodes from l1
or l2
.您永远不应该将
current.next
分配给来自l1
或l2
节点。 Instead you must create a new ListNode
that has the same value as l1
or l2
and make current.next
point to your new ListNode
.相反,你必须创建一个新
ListNode
具有相同的值l1
或l2
并current.next
点到新ListNode
。 Otherwise you're trying to straighten a bowl of spaghetti, which is an impossible task.否则你会试图把一碗意大利面弄直,这是一项不可能完成的任务。 You need to build your own new strand of spaghetti.
你需要建立自己的新意大利面条链。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.