值为 null 的引用类型的类型?

发布于 2024-11-02 02:29:46 字数 1105 浏览 1 评论 0原文

根据: http://java.sun.com/docs/ books/jls/second_edition/html/typesValues.doc.html
4.5.2 引用类型变量
引用类型可以保存null引用。

当赋值为null时,是否可以检索引用类型的声明类型?

具体来说,在使用反射的方法中,我希望该方法是空安全的并作用于原始声明的类型(尽管我知道以下代码片段不起作用),例如:

String referenceType = null;
MyReflectionClass.reflectionMethod(referenceType);
...
public static void reflectionMethod(Object referenceType) {
   Class<?> declaredType = referenceType.getClass();
}

我不会反对使用泛型如有必要,使用类型 T 而不是 Object 作为声明的参数类型。

编辑:我知道.getClass()适用于实例,而不是声明的类型。我想知道是否可以向参考询问它的声明类型。由于类层次结构是静态的,因此获取该信息应该没有问题。

编辑2:这里,情况已经明确:Java“pass-按引用”还是“按值传递”?
Java只是按值传递,因此即使使用引用类型,它也总是像传递值(对象实例)一样进行处理(即使内部仅传递对象指针)。这意味着 Java 实际上没有一个知道其类型的引用类型(至少就程序员而言),它全部位于值实例中。
因此不可能确定任何 null 值的类型。

According to:
http://java.sun.com/docs/books/jls/second_edition/html/typesValues.doc.html
4.5.2 Variables of Reference Type
A reference type can hold a null reference.

Is it possible to retrieve the declared type of the reference type when the assigned value is null?

Specifically, in a method that uses reflection, I wish the method to be null-safe and act on the original declared type (though I know the following code snippet doesn't work), for instance:

String referenceType = null;
MyReflectionClass.reflectionMethod(referenceType);
...
public static void reflectionMethod(Object referenceType) {
   Class<?> declaredType = referenceType.getClass();
}

I would not be averse to using generics to have type T instead of Object as the declared parameter type, if necessary.

Edit: I know that .getClass() works on the instance, not the declared type. I was wondering if it was possible to ask the reference for it's declared type. Since class hierarchies are static, there should be no problem to get that information.

Edit2: Here, the situation is made clear: Is Java "pass-by-reference" or "pass-by-value"?
Java is only pass-by-value, so even though a reference type is used, it is always handled as if the value (object instance) is passed (even though the internals only pass an object pointer). This means that Java doesn't actually have a reference type that knows about it's type (at least as far as the programmer is concerned), it's all in the value instances.
Therefore it is impossible to determine the type of any null value.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(5

我的奇迹 2024-11-09 02:29:46

简而言之,不。但是,尝试查找空引用的成员并没有多大意义,因为空意味着不存在任何内容。您可能最好禁止 null 作为输入,可能通过抛出 NullPointerException 来实现。

如果必须处理 null,也许最好的方法是显式传递类引用(或者更好的是直接引用相关方法)。

public static void reflectionMethod(Object param, Class<?> referenceType) // null is dis-allowed for referenceType
{
    // ... no need to try to back-track the type from an object
}

如果您只能获得空值,则很难(除非施加其他约束,否则不可能)比非常幸运的猜测做得更好。

In a single word, no. It doesn't make a whole lot of sense to try to find the members of a null reference, though, since null implies the absence of anything. You're probably better off just dis-allowing null as an input, probably by throwing a NullPointerException.

If you must handle null, perhaps the best way is to explicitly pass the class reference (or even better, a direct reference to the method in question).

public static void reflectionMethod(Object param, Class<?> referenceType) // null is dis-allowed for referenceType
{
    // ... no need to try to back-track the type from an object
}

If you can only ever get the null value, it's difficult (impossible unless there are other constraints imposed) to do much better than having a very lucky guess.

方圜几里 2024-11-09 02:29:46

你误会了。 getClass() 不会告诉您变量 的声明类型,它会告诉您对象 的类型(如果有的话)。让我们停下来退后一步 - 如果它确实如此,您会指哪个变量?原始变量?方法参数?在此过程中它还传递了任何其他变量吗?那将是彻底的疯狂。

You misunderstand. getClass() doesn't tell you the declared type of the variable, it tells you the type of the object, if there is one. And let's stop and take a step back for a minute - which variable would you be referring to, if it did that? The original variable? The method parameter? Any other variable that it passed through along the way? That would be total madness.

随风而去 2024-11-09 02:29:46

您找不到 null 引用的声明类型。泛型也没有什么帮助,因为它们在编译时就被删除了。如果您需要知道 null 情况的类型,则必须以某种方式在运行时传递该类型。

You can't find the declared type of a null reference. Generics can't really help either, as they're erased at compile time. Some way or another you'll have to pass the type at runtime if you need to know it for the null case.

何处潇湘 2024-11-09 02:29:46

不,不是。在您的示例中,当尝试调用空引用引用类型上的方法时,您将收到空指针异常。

更具体地说,这是不可能的,因为在编译时不一定知道具体类型,例如,如果我声明对象类型的引用并将其分配给字符串,那么您的方法应该发现该对象是字符串而不是对象。

Object referenceType= new String("I'm a string");
MyReflectionClass.reflectionMethod(referenceType);
...
public static void reflectionMethod(Object referenceType) {
   Class<?> declaredType = referenceType.getClass(); // returns String.class
}

No it is not. In your example you will get a null pointer exception when trying to call a method on the null reference referenceType.

More specifically it is not possible because the concrete type is not neccesarily known at compile time, e.g. if I declare a reference of type Object and assign it to a String then your method should discover that the object is a String not an Object.

Object referenceType= new String("I'm a string");
MyReflectionClass.reflectionMethod(referenceType);
...
public static void reflectionMethod(Object referenceType) {
   Class<?> declaredType = referenceType.getClass(); // returns String.class
}
日记撕了你也走了 2024-11-09 02:29:46

我不确定这对您的上下文是否有帮助,但您可以使用泛型来实现类似的功能 - Java 1.5+ 保留子类的类型信息。

package spikes;

import java.lang.reflect.ParameterizedType;

public class ReflectMethod {
    public abstract static class GenericType<T> {
        public Class typedClass() {
            ParameterizedType pType = (ParameterizedType) getClass().getGenericSuperclass();
            return (Class) pType.getActualTypeArguments()[0];
        }

        public void reflectMethod(T o) {
            System.out.println("Class: " + typedClass());
        }
    }

    /**
     * @param args
     */
    public static void main(String[] args) {
        GenericType<String> gs = new GenericType<String>() {

        };
        gs.reflectMethod("");
    }
}

I am not sure this is helpful in your context, but you can use generics for achieving something similar - Java 1.5+ keeps type information for the subclass.

package spikes;

import java.lang.reflect.ParameterizedType;

public class ReflectMethod {
    public abstract static class GenericType<T> {
        public Class typedClass() {
            ParameterizedType pType = (ParameterizedType) getClass().getGenericSuperclass();
            return (Class) pType.getActualTypeArguments()[0];
        }

        public void reflectMethod(T o) {
            System.out.println("Class: " + typedClass());
        }
    }

    /**
     * @param args
     */
    public static void main(String[] args) {
        GenericType<String> gs = new GenericType<String>() {

        };
        gs.reflectMethod("");
    }
}
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文