8

私は現在、将来のプロジェクトのためにScalaを評価していますが、何か奇妙なことに遭遇しました。JSPで次の定数を作成しました。

val FORMATED_TIME = "formatedTime";

そして、それは機能しませんでした。いくつかの実験の後、私はそれの底に到達するために逆コンパイルすることにしました:

private final java.lang.String FORMATED_TIME;

public java.lang.String FORMATED_TIME();
  Code:
   0:   aload_0
   1:   getfield    #25; //Field FORMATED_TIME:Ljava/lang/String;
   4:   areturn

今それは面白いです!個人的には、インスペクターが異なる名前空間に存在するため、なぜインスペクターがプレフィックスgetを必要とし、ミューテーターがJavaでプレフィックスセットを必要とするのか疑問に思っていました。

ただし、それをチームの他のメンバーに説明するのはまだ厄介かもしれません。それで、検査官なしで公の定数を持つことは可能ですか?

4

2 に答える 2

11

これは、Uniform Access Principleによるものです。つまり、メソッドとフィールドは区別できません。

この回答を参照してください

Scala 2.8.0 では、コンパニオン オブジェクトがある場合、静的フォワーダーが失われることを意味します)

これが Scala にある場合:

//Scala
object CommonControler {
      val FORMATED_TIME = "formatedTime";
}

Javaからこのように使用できます

//Java

// Variables become methods
CommonControler$.MODULE$.FORMATED_TIME();
// A static forwarder is avaliable
CommonControler.FORMATED_TIME();

本Scala in Depthも参照してください

クラスの@scala.reflect.BeanPropertyにも注意してください。

于 2010-10-05T13:10:43.110 に答える
1

逆コンパイルされたコードをさらに調べたところ、別のことがわかりました。変数は実際には静的ではありません。したがって、私の次のアイデアは、代わりにオブジェクトを使用することでした:

object KommenControler
{
   val FORMATED_TIME = "formatedTime";
} // KommenControler

しかし、今では物事は本当に醜いものになります:

public final class ….KommenControler$ extends java.lang.Object implements scala.ScalaObject{

public static final ….KommenControler$ MODULE$;

private final java.lang.String FORMATED_TIME;

public static {};
  Code:
   0:   new #9; //class …/KommenControler$
   3:   invokespecial   #12; //Method "<init>":()V
   6:   return

public java.lang.String FORMATED_TIME();
  Code:
   0:   aload_0
   1:   getfield    #26; //Field FORMATED_TIME:Ljava/lang/String;
   4:   areturn

そのため、MOUDLE$ というシングルトン インスタンスを持つ $ で終わる追加のクラスを取得します。そして、まだ検査官がいます。したがって、jsp 内の変数へのアクセスは次のようになります。

final String formatedTime = (String) request.getAttribute (….KommenControler$.MODULE$.FORMATED_TIME ());

これは期待どおりに機能し、個人的には我慢できますが、それをチームにどのように説明すればよいでしょうか?

もちろん、もっと簡単な方法があれば聞きたいです。

于 2010-10-05T08:45:02.750 に答える