【问题标题】:When is an unassigned expression a valid statement?什么时候未赋值的表达式是有效的语句?
【发布时间】:2015-09-04 20:23:52
【问题描述】:

我读过Oracle's expressions tutorial 并无法理解这一点。

众所周知,以下代码行是有效的 Java 语法:

new Object();

但是,当我尝试使用原始表达式时:

(3 + 2);

Eclipse 显示“赋值的左侧必须是变量”的编译错误。

这不仅适用于原语,也适用于字符串文字:

"arbitraryString";

那么,未赋值表达式作为 Java 代码行有效的规则是什么?

【问题讨论】:

    标签: java


    【解决方案1】:

    规则在Java Language Specification:

    某些类型的表达式可以用分号作为语句。

    表达式语句:

    • 语句表达式;

    语句表达式:

    • 作业
    • PreIncrementExpression
    • PreDecrementExpression
    • 后增量表达式
    • PostDecrementExpression
    • 方法调用
    • ClassInstanceCreationExpression

    您会看到构造函数调用是一个语句。但字符串文字或数学表达式不是。

    【讨论】:

    • 这是对 OP 问题的回答:“规则是什么”
    【解决方案2】:

    创建对象或调用或方法可能会产生副作用,我认为这是主要原因,而算术表达式不会发生任何事情。

    【讨论】:

      【解决方案3】:

      仅包含行

      new Object(); 
      

      或者更准确地说

      new SomeClass(); 
      

      是可以接受的,因为SomeClass()构造函数的代码可能是我们想要的。

      但如果行只包含

      "foo";
      

      或

      2;//or (2+3);
      

      编译器知道,除了创建/重用字符串字面量或整数字面量之外,这段代码不会做任何其他事情,这意味着它可能是某种程序员的错误,因此编译器无法接受。

      【讨论】:

      • 您的回答很有道理,但 OP 的问题是“规则是什么”,而不是“差异的原因是什么”。
      • @CPerkins 是的,但我经常发现 reasoning 比 rule 更容易记住/理解,所以我暂时留下这个答案 :)跨度>
      【解决方案4】:

      您正在寻找表达式和表达式语句之间的区别。像myVoid(); 这样的语句可以写成语句:这些是 void 方法等(这是你知道的部分)。像(3 + 2); 和"arbitraryString" 这样的表达式没有副作用。它们只能被视为一个值,因为不执行任何代码。表达式语句,如new Object(); 可能有副作用并执行代码,有时您只希望执行此代码而忽略返回值。因此编译器允许这样做。

      【讨论】:

      • 然而,someString + "..." 可能有副作用——如果编译器/解释器足够笨并且堆中几乎没有剩余内存,它可能会导致 OutOfMemory 错误
      • @SargeBorsch 我说的是现实场景。在极端情况下,几乎任何事情都可能导致一些晦涩的错误,但是学习 Java 的人需要了解具体规则吗?我可以告诉你我没有。
      猜你喜欢
      • 2018-03-04
      • 2021-11-23
      • 2021-06-10
      • 2017-12-28
      • 2018-10-22
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多