1

Is there anyway to obtain an instance of a class called in another class? For example, if Foo class has an instance of a Bar class and a Clazz class, is there anyway to obtain the instance of the Bar class through the Clazz class using reflection?

public class Foo{
  Bar b = new Bar();
  Clazz c = new Clazz();
}

public class Bar
{
   int i = 3;
}

public class Clazz
{
  //Code to get the instance of Bar running in Foo using Reflection
}
Jason C
  • 38,729
  • 14
  • 126
  • 182
Alan W
  • 291
  • 1
  • 5
  • 18

1 Answers1

0

There is no "instance of Bar running in Foo", since you have not instantiated a Foo. And no, as it stands, Clazz has no knowledge of any classes that may refer to it in a field, you would have to add that.

One way to do this is via proper use of getters and keeping track of the parent object:

public class Foo {
    Bar b = new Bar();
    Clazz c = new Clazz(this); // be warned: `this` is not fully constructed yet.
    public Bar getB () { return b; }
}

public class Clazz {
    private final Foo owner;
    public Clazz (Foo owner) {
        this.owner = owner;
    }
    public void example () {
        doSomething(owner.getB());
    }
}

Or, even better, since Clazz no longer depends on Foo and you don't have to worry about a partially constructed Foo, just pass the Bar to Clazz:

public class Foo {
    Bar b = new Bar();
    Clazz c = new Clazz(b); 
}

public class Clazz {
    private final Bar bar;
    public Clazz (Bar bar) {
        this.bar = bar;
    }
    public void example () {
        doSomething(bar);
    }
}

The second way more naturally indicates your actual dependencies as well (Clazz doesn't care that it comes from a Foo, it only cares about having a Bar).

The first way has the advantage of allowing Foo to change its Bar at any point (I noticed you did not declare final b in Foo) and have Clazz be aware of the updated value; of course, that same thing can be accomplished with a Clazz#setBar(Bar b) without introducing a false dependency on Foo.


There isn't much need for reflection there. However, responding to your comment below, where you write:

The actual purpose of my question regards to a battleship tournament we are having in a CS class at my University. We are allowed to hack each other in order to find the ship deployment of our adversary.

Unfortunately, then -- presuming your snippet is an accurate representation of the code structure -- unless Clazz stores an instance of the Foo that created it (or is a non-static inner class of a Foo), you are out of luck. There is no way with reflection to find the Foo that has that Clazz (and thus get the Bar), because reflection does not provide a means of getting a list of all instantiated Foos to search through. If you know the Foo then you can get its b member, but you have to know about the Foo instance to begin with. You might be able to inject some clever byte code somewhere to track it though, a bit advanced but see Java Bytecode Instrumentation, or here for an overview.

You then write:

I have read that there is a way to find the instance of the Foo class through reflection if you know the name of the class.

No, unfortunately (if I understand you correctly), there is no way to get an existing instance of a Foo given only its class name.

Is there anyway for me to find the Bar class if I find the Foo class?

If you have an instance of a Foo, and you know the field name is b, then you can do:

Foo theFoo = ...; // your Foo instance

Field field = Foo.class.getDeclaredField("b");
Bar theBar = (Bar)field.get(theFoo); // get field "b" value from 'theFoo'.

See Class.getDeclaredField() and Field.get().

Community
  • 1
  • 1
Jason C
  • 38,729
  • 14
  • 126
  • 182
  • I undesrtand what you are saying, but my example was just a general example for what I was trying to achieve. The actual purpose of my question regards to a battleship tournament we are having in a CS class at my University. We are allowed to hack each other in order to find the ship deployment of our adversary. That is the reason why I wanted to know how to get the name of a class or an instance through reflection. – Alan W Apr 03 '14 at 22:19
  • Well I do know what the name of the Foo class is. I have read that there is a way to find the instance of the Foo class through reflection if you know the name of the class. Is there anyway for me to find the Bar class if I find the Foo class? – Alan W Apr 03 '14 at 22:32
  • @AlanW I've updated my answer with answers to your comments as well as an example snippet. – Jason C Apr 03 '14 at 22:38