【问题标题】:Java does not de-compile correctlyJava 没有正确反编译
【发布时间】:2016-06-07 16:58:42
【问题描述】:

我正在为 android 开发并使用 jitpack.io 从 git 编译 gradle

我正在尝试使用 git 中的这个库进行函数式编程:

fj - functional programmming for Java 7

即使所有内容都经过测试,我也运行了代码并得到了错误。

问题出在 GroupBy 类中:

源代码:

public Collection<Group<S,T>> execute(Collection<T> collection){
    Hashtable<S, Group<S, T>> groups = new Hashtable<S, Group<S, T>>();

    for (T item: collection){
        S classification = grouper.select(item);

        if (!groups.contains(classification)){
            groups.put(classification, new Group<S, T>(classification));
        }
        groups.get(classification).add(item);
    }

    return groups.values();
}

反编译代码:

public Collection<GroupBy.Group<S, T>> execute(Collection<T> collection) {
    Hashtable groups = new Hashtable();

    Object item;
    Object classification;
    for(Iterator var3 = collection.iterator(); var3.hasNext(); ((GroupBy.Group)groups.get(classification)).add(item)) {
        item = var3.next();
        classification = this.grouper.select(item);
        if(!groups.contains(classification)) {
            groups.put(classification, new GroupBy.Group(classification));
        }
    }

    return groups.values();
}

如果有任何帮助,我将不胜感激。

目前我看不出代码看起来不同的任何原因

谢谢

【问题讨论】:

  • 反编译器实际上不会反编译为确切的源代码。因为它只看到字节码,它会尝试反编译为尽可能接近源代码的东西,但即使它应该做同样的事情,你也永远不会真正得到你以前拥有的确切代码
  • 好的。我得到了答案... 1. 反编译的代码完全一样。这只是编译器2的代码转换和优化。我遇到的错误是因为我使用'contains'而不是'containKey'

标签: java android functional-programming java-7 jitpack


【解决方案1】:

简短的回答是,当编译 java 时,信息会丢失。但是反编译后的代码和你写的代码完全一样。

让我们逐行看......

public Collection<GroupBy.Group<S, T>> execute(Collection<T> collection) {

这是相同的,尽管它的全名是 Group 类。

    Hashtable groups = new Hashtable();
    Object item;
    Object classification;

正如您在此处看到的,变量名称和所有通用信息都丢失了。 java 中的泛型可以被认为是对编译器的提示,以检查错误。一旦编译器完成编译,信息就会被丢弃(通常)。

    for(
        Iterator var3 = collection.iterator(); 
        var3.hasNext();                         
        ((GroupBy.Group)groups.get(classification)).add(item)
    ) {

增强的 for 循环已被经典的 for 循环所取代。这是因为在字节码中它们是相同的东西(尽管更聪明的反编译器可能已经发现了这一点并在此处编写了增强的 for 循环)。

这里的另一个有趣的事情是编译器已将groups.get(...).add(...) 语句放入您的 for 循环中。如果您考虑for(initialisation; termination; increment) 的合约,那么increment 会在每次循环迭代时发生。因此,即使您在循环中编写语句,效果也是一样的。 [这样做可能有充分的理由,虽然我不是编译器专家,所以我不能肯定]。

        item = var3.next();
        classification = this.grouper.select(item);
        if(!groups.contains(classification)) {
            groups.put(classification, new GroupBy.Group(classification));
        }
    }

    return groups.values();
}

其余代码与您编写的几乎完全相同。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2017-12-12
    • 2011-07-04
    • 2018-07-22
    • 2016-02-28
    • 2011-02-19
    • 2014-07-12
    • 2021-03-25
    • 1970-01-01
    相关资源
    最近更新 更多