【问题标题】:How to let JVM know about custom marker interface in java如何让 JVM 知道 java 中的自定义标记接口
【发布时间】:2020-01-03 14:44:14
【问题描述】:

是否可以在java中编写我们自己的标记接口。我正在编写类似

的代码
public interface MyMarker {

}

那是标记界面吗?

如果可能的话,我如何让JVM知道这个接口是我自己创建的标记接口?

【问题讨论】:

  • 请问你想用marker界面解决什么样的问题?也许有人可以提出另一种模式。

标签: java


【解决方案1】:

是的,这是一个标记界面。您将测试一个对象是否“实现”它,如下所示:

if (x instanceof MyMarker)

对于您想要的特定(而不是对象)

if (MyMarker.isAssignableFrom(otherClass))

您应该考虑使用注释而不是标记接口。它们并不总是直接替换,但在许多情况下,它们用于相同的目标,并且注释 (IMO) 更清晰。

【讨论】:

  • 但是每个标记界面都有自己的属性..我如何设置我的标记界面属性?
  • @Abhisek:你什么意思?你能举个例子吗?
  • 你能给我一个简短的例子吗?
  • 像可序列化接口一样,它具有对象感知属性。就像我在 perticuler 类中实现可序列化接口一样,我们将能够将该类的对象的值持久保存在永久存储设备中。我想用我的标记界面做那种独特的属性..这可能吗?
  • @Abhisek:这完全取决于你正在实施什么。这背后没有魔法。您仍然需要编写代码来实现您想要的任何行为 - 您只需使用上面显示的测试之一来确定对象或类是否使用了您的标记接口。 (正如我所说,IMO 最好使用注释。)
【解决方案2】:

我们不能说没有任何方法的接口是标记接口。因为“标记”这个词本身就表示“标记某物”的意思。所以我说,接口(无论它的内容是什么)通过实现,如果一个类获得一些额外的或专门的行为,比如允许对象存储到持久性存储(可序列化)或允许对象使其重复或复制(可克隆)或者只允许用户实现一种方法(如 run()),而不是在线程编程(Runnable)的子类中实现近 4 t0 5 个方法。

这些是对象在实现那些只是称为 MARKER INTERFACE 的接口时可以获得的特殊行为。

结论

标记接口可能包含也可能不包含方法...

它也可以称为标记接口,虚拟接口,空接口......

【讨论】:

    【解决方案3】:
    1. “通常”标记接口用于向编译或 JVM 发出处理“标记类型”对象时可能需要的附加元数据的信号。

    2. 例如, 如果一个类使用 java.io.Serializable 接口,则编译实际上会为该类生成该标记接口的实现代码,JVM 在运行时存储/编组该对象时需要该代码。

    3. 所以我看不到自定义标记接口的任何实际用途(因为它对于在 java 中的有限标记接口集上工作的编译器/JVM 没有任何意义)

    【讨论】:

    • 你能告诉我这些类型的 iterface(可序列化等)有什么特别之处,每当我们在我们的类中使用它们时,它们的行为与其他接口不同,尽管这些接口不包含任何内容(因为它们被称为标记界面)
    • @Abhisek:抱歉迟到了。正如我所提到的,标记接口就像编译器的特殊指令,用于生成附加代码,以便 JVM 在运行时为该标记接口的特殊用途提供服务。例如,在 java.io.Serializable 的情况下,编译会在类文件中添加一些附加信息,以帮助 JVM 进行序列化。这就是为什么标记接口的行为不同,因为编译器对它们的处理方式不同。
    【解决方案4】:

    实现接口的类获得了一些特殊的品质,即接口被称为标记或标记接口。

    例如: 一个类实现 Runnable 接口,该类充当线程。所以它被称为标记接口。

     A class implements java.io.Serializable interface that clsass act to send object class which is needed at run time by JVM while storing/marshaling that object.
    
     A Class implements java.lang.Clonable interface that object ready to cloning. so java.lang.Clonabel interface is called Marker or Taged interface.
    

    有些人认为所有空接口都是标记接口。但这是不正确的。

    因为我们采用 java.lang.Runnable 接口它不是它包含的空接口 方法称为 void run()。

    在 java API 中,所有标记接口都是空的,如 java.io.Serializable。

    一些 Marker 接口或不为空,如 java.lang.Runnable。

    【讨论】:

      猜你喜欢
      • 2019-07-13
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2014-10-01
      • 2016-11-30
      • 1970-01-01
      • 2020-04-17
      • 2016-03-03
      相关资源
      最近更新 更多