In R, How to Check If Two Variable Names Reference the Same Underlying Object

In R, how can I check if two variable names reference the same underlying object?

You can use the .Internal inspect function:

A <- 1:10
B <- A
.Internal(inspect(A))
# @27c0cc8 13 INTSXP g0c4 [NAM(2)] (len=10, tl=0) 1,2,3,4,5,...
.Internal(inspect(B)) # same
# @27c0cc8 13 INTSXP g0c4 [NAM(2)] (len=10, tl=0) 1,2,3,4,5,...
B[1] <- 21
.Internal(inspect(B)) # different
# @25a7528 14 REALSXP g0c6 [NAM(1)] (len=10, tl=150994944) 21,2,3,4,5,...

Simon Urbanek has written a simple package with similar functionality. It's called... wait for it... inspect. You can get it from R-forge.net by running:

install.packages('inspect',repos='http://www.rforge.net/')

UPDATE: A word of warning:

I recommend you use Simon's package because I'm not going to recommend you call .Internal. It certainly isn't intended to be used interactively and it may very well be possible to crash your R session by using it carelessly.

Value/reference equality for same named function in package/namespace environments?

They are pointers to the same object. Using this answer to another question, we can check if two objects refer to the same place in memory.

are_same <- function(x, y)
{
f <- function(x) capture.output(.Internal(inspect(x)))
all(f(x) == f(y))
}

are_same(nsSd, pkgSd) #TRUE
are_same(1:5, 1:5) #FALSE

Two reference pointing to the same object in memory but works independently in java?

You are conflating "object" and "reference". For example in the sentence

For example here:

Look at this code in the traverse(),

Node currentNode = this.top;

here an object of type Node is created that points to the already
existing this.top node object.

No object of type Node is created here (there is no new, that's how you know).

What is defined here is a (local) variable of type Node. And the reference that is stored in this.top is also assigned to currentNode.

So it means, two references
pointing to the same object in memory isn't it?

Yes, this part is again correct.

Think of a reference like a sheet of paper. The paper can be empty (i.e. the reference is null) or it can have some address written on it (i.e. it points to some object).

Now currentNode is a piece of paper that happen to have the same address written on it that this.top also has written on it (it's a tiny bit more complicated, because this is a piece of paper written on it and if you look at that address then you'll find some other piece of paper labelled top that has some address written on it, but that doesn't fundamentally change how this works).

At some point later in the code currentNode gets reassigned (i.e. the content of the piece of paper gets changed). First to a different address (i.e. the address scribbled out and replaced with another one) and then eventually with null (i.e. you scribble out the content and leave it "blank").

But just because you wrote on that piece of paper doesn't mean that the other piece of paper (found via this.top) has changed. There is no reason for to it change: they are two independent pieces of paper that at one point happen to have had the same stuff written on them.

Or put differently: assigning a new value to currentNode has absolutely no effect on the object previously referenced by currentNode.

If you had done currentNode.nextLink = null instead of (basically) currentNode = null then that would be different:

  • currentNode = null means "remove the address written on the piece of paper labelled currentNode.
  • currentNode.nextLink = null means "go to the address written on the piece of paper labelled currentNode, there find a piece of paper labelled nextLink and remove the address written on it.

The first one just changes the reference currentNode and the second one actually changes the object pointed to by currentNode.

Edit: it seems your confusion stems from the debugging view where it says currentNode = {StackWithLinkedList$Node@801}. You seem to interpret this as "currentNode is the object {StackWithLinkedList$Node@801}", but that's not what it means.

currentNode is never an object. It can't be. Java variables/fields can't hold objects. So what that display really means is: currentNode currently references the object represented as {StackWithLinkedList$Node@801}.

Two newly created objects seem to refer to the same address

Because you are passing a reference to numbers without making a copy, so both objects end up pointing to the same int[] instance. While there are two different outer objects, the inner object that they both point to is the same object, hence you can change that inner object by dereferencing either of AText.numbers and BText.numbers, and the change will be visible in both of the outer objects when accessing their numbers fields.

You can check that AText == BText will return false, but AText.numbers == BText.numbers will return true. And this.numbers == AText.numbers will also return true.

Like try this same code but with this constructor:

public LabelText(char letter, int[] numbers) {
this.letter = letter;
this.numbers = numbers.clone(); // so it will always be unique array here
}

How to check if object (variable) is defined in R?

You want exists():

R> exists("somethingUnknown")
[1] FALSE
R> somethingUnknown <- 42
R> exists("somethingUnknown")
[1] TRUE
R>


Related Topics



Leave a reply



Submit