【问题标题】:Java synthetic method and bridge method confusionJava合成方法和桥接方法混淆
【发布时间】:2017-12-04 09:50:56
【问题描述】:

正如Java Tutorial 中所述,桥接方法意味着它也是一种合成方法。问题是,isSynthetic 方法的调用是否有可能返回 true,但 isBridge 方法对于 Method 对象返回 false,即,如果一个方法是合成的,是否意味着它也是一个桥方法?

不完全相同,但isSyntheticisBridge 方法的源代码如下所示:

static final int SYNTHETIC = 0x00001000;
public boolean isSynthetic() {
    return (getModifiers() & SYNTHETIC) != 0;
}

static final int BRIDGE = 0x00000040;
public boolean isBridge() {
    return (getModifiers() & BRIDGE) != 0;
}

为什么isBridge 方法体不像return isSynthetic();

【问题讨论】:

  • 这些方法只是返回对应修饰符的值;该类可能只是一个数据持有者。至关重要的是如何设置修饰符的逻辑。
  • 我也是这么想的。修饰符是通过构造函数设置的。但我找不到它的用法。

标签: java reflection java-synthetic-methods


【解决方案1】:

如果您只是在寻找这样的示例:

Function<String, Integer> func = s -> s.length();

Arrays.stream(DeleteMe.class.getDeclaredMethods())
     .peek(m -> System.out.println(m.getName() + " isSynth : " + m.isSynthetic() + " isBridge : " + m.isBridge()))
     .forEach(System.out::println);

会有类似的条目:

lambda$0 isSynth : true isBridge : false
lambda$1 isSynth : true isBridge : false

【讨论】:

  • 另一个例子是当内部类访问外部类的private 成员时生成的access$n 方法,反之亦然。
  • @Holger 没想到这些 :)
【解决方案2】:

桥是合成的,但合成不一定是桥。示例:

public class Test {

    public Test clone() {
        return null;
    }

字节码大纲:

  // access flags 0x1041
  public synthetic bridge clone()Ljava/lang/Object; throws java/lang/CloneNotSupportedException 
   L0
...

【讨论】:

  • 我通过在您的 Test 类上调用 getDeclaredMethods() 获得了两个克隆方法。其中之一是合成和桥接。
  • clone() 与 Object 返回类型是编译器创建的用于覆盖 Object.clone() 的桥接方法。编译器创建的所有隐式方法都是合成的,但它们的创建目的不同。
  • 我知道什么是合成的,我只是想指出您的答案需要澄清。您提供的内容不足以阐明您的结论。
【解决方案3】:

是否有可能调用 isSynthetic 方法返回 true 但 isBridge 方法对于 Method 对象返回 false

是的,这是可能的。

例如,方法AbstractPipeline.lambda$spliterator$0()synthetic 但它不是 bridge

根据JVM Spec

  • ACC_SYNTHETIC 标志表示此方法是由编译器生成的,不会出现在源代码中
  • ACC_BRIDGE 标志用于指示编译器为 Java 编程语言生成的桥接方法。

所以,

  • bridge 方法 100% 确定它是 synthetic
  • 不需要synthetic 方法bridge

更多关于bridge方法

基于this articlebridge 方法由 Java 编译器生成,用于 Java 泛型的 type erasure

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2011-10-08
    • 2014-01-13
    • 1970-01-01
    • 1970-01-01
    • 2016-04-02
    • 2014-04-15
    • 1970-01-01
    • 2011-06-27
    相关资源
    最近更新 更多