静态方法无法访问调用者类名。

huangapple go评论75阅读模式
英文:

static method can't access caller class name

问题

I have 2 classes A and B where B extends A. Both class are having a static variable x. There is one static method defined in class A which is accessing x. When I call the method with B from main, is there any way to know the caller of the function? With that caller class name I can use reflection in order to get value of x from class B.

    public class Test {
        public static void main(String[] args) throws Exception {
            A a = new A();
            B b = new B();
            b.amthu();
        }
        private static class A {
            public static String x = "static string from A";
            public static void amthu() throws NoSuchFieldException, IllegalAccessException {
                System.out.println(/* 这里可以是什么代码? */);
            }
        }
        private static class B extends A {
            public static String x = "static string from B";
        }
    }

I have similar code in python which works fine because of the class method having cls as arguments but static method doesn't have such thing and in Java I am only aware of static methods so can't access value of x from sub-class B.

    class A:
        x = "static value of A"
    
        @classmethod
        def amthu(cls):
            print(getattr(cls, "x", None))
    
    
    class B(A):
        x = "static value of B"
    
    
    a = A()
    b = B()
    b.amthu()
英文:

I have 2 classes A and B where B extends A. Both class are having a static variable x. There is one static method defined in class A which is accessing x. When I call the method with B from main, is there any way to know the caller of the function? With that caller class name I can use reflection in order to get value of x from class B.

public class Test {
    public static void main(String[] args) throws Exception {
        A a = new A();
        B b = new B();
        b.amthu();
    }
    private static class A {
        public static String x = "static string from A";
        public static void amthu() throws NoSuchFieldException, IllegalAccessException {
            System.out.println(/* what can be the line here?*/);
        }
    }
    private static class B extends A {
        public static String x = "static string from B";
    }
}

I have similar code in python which works fine because of the class method having cls as arguments but static method doesn't have such thing and in Java I am only aware of static methods so can't access value of x from sub-class B.

class A:
    x = "static value of A"

    @classmethod
    def amthu(cls):
        print(getattr(cls, "x", None))


class B(A):
    x = "static value of B"


a = A()
b = B()
b.amthu()

答案1

得分: 1

`A.amthu()` 方法无法检测到它是通过类型为 `B` 的变量调用的。

Java 中的静态方法具有诸如此类的基本限制。正是因为这些限制,你在 Java 中并不经常看到静态方法的使用。特别地,不鼓励使用对象实例(如 `b.amthu()`)来调用静态方法,因为这会导致混淆 - 请参阅 https://stackoverflow.com/questions/610458/why-isnt-calling-a-static-method-by-way-of-an-instance-an-error-for-the-java-co

你可以通过将期望的类作为变量传递给 `A.amthu` 来解决这个问题:

    // 调用方法
    A.amthu(B.class);

    // 在 A 中的方法声明
    static void amthu(Class<? extends A> klass) { ... }

或者,你可以重新设计你的代码,完全避免使用静态字段和方法。不过,如果不知道你在尝试做什么,就无法告诉你具体会是什么样子。
英文:

There is no way the A.amthu() method can detect it was called using a variable of the type B.

Static methods in Java have fundamental limitations such as this. These limitations are why you don't see static methods used very much in Java. In particular, calling static methods using object instances like b.amthu() is discouraged because it leads to confusion - see also https://stackoverflow.com/questions/610458/why-isnt-calling-a-static-method-by-way-of-an-instance-an-error-for-the-java-co

You can get around this by passing the class you expect as a variable to A.amthu:

// call method
A.amthu(B.class);

// method declaration in A
static void amthu(Class&lt;? extends A&gt; klass) { ... }

Or perhaps you can rework your code to avoid using static fields and methods altogether. It's impossible to tell you what that would look like without knowing what you're trying to do here though.

答案2

得分: 0

你可以进行 instanceof 检查,然后打印 B.x 或 A.x。

如果 (this instanceof A)
System.out.println A.x
否则
System.out.println B.x

英文:

You can do instanceof check and then print B.x or A.x

If(this instanceof A)
System.out.println A.x
else
System.out.println B.x

huangapple
  • 本文由 发表于 2020年8月16日 22:38:21
  • 转载请务必保留本文链接:https://go.coder-hub.com/63438162.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定