2017-05-24 14 views
1

私はScalaでPythonからいくつかのことを試しています。 Scalaは一貫性のあるタイプを維持について多くのより厳密なので、私はPythonで爆破と思われる、私は以下の連結を行うことができますことを見つけるために驚いた:ScalaでStringとIntを連結できないのはなぜですか?

def adder(one:Any, two:String) = {one+two} 

adder("word", "suffix") 

res13:文字列= wordsuffix

しかし、また:

val x:Int = 1 

adder(x, "suffix") 

res12:文字列= 1suffix

  • だから、それはちょうど私に言ってStringワット/アウトにIntを変換します。これは何と呼ばれ、その背後にある論理は何ですか?

  • そして、これの利点は何ですか?私はそれが私をかむために戻ることができると感じます。関数へのユーザー入力を処理するとき

私は、これは非常に具体的ではありません知っていて、これが広すぎる場合、私は喜んで質問を撤回ます。

+1

あなたの質問が本当に** _理由_ ** **これはスカラーではなく** _ how _ **これが行われている場合、私はこれがこのように行われたと考えています。文字列変換](https://docs.oracle.com/javase/specs/jls/se7/html/jls-5.html#jls-5.4)および.NET(歴史的追加ターゲットプラットフォーム)でも同様に動作します。それがなぜあるのかについては、いくつかの典型的な用途の利便性のために考えています。 – SergGr

答えて

3

Any + Stringを実装する任意のタイプ

implicit final class any2stringadd[A](private val self: A) extends AnyVal { 
    def +(other: String): String = String.valueOf(self) + other 
    } 

(あなたがadderでそれを定義したもの)のオブジェクト上で動作しscala.Predefにおける暗黙のクラスがあります。言及された悪党のように、String + Anydefined in StringOpsを連結する方法もあります。 Any + Anyを実行しようとすると、引数としてStringが必要になるため、失敗します。

だから、それはちょうど私

を言って外に/ wを文字列に変換のIntを変換ScalaはStringにあなたのIntに変換されますが、IntStringに強制することはできませんので、それは型変換ではありません。あなたはこのような何かを試みることによってそれを観察することができます。

Scalaは魔法 StringIntを強制することはできませんので、コンパイルに失敗します

その背後にある論理は何ですか?

implicit classes

を参照してください。そして、これの利点は何ですか?私はそれが私をかむために戻ることができると感じます。関数へのユーザー入力を処理するとき

これは、Stringと連結に特有の便利な方法です。この機能はJavaで実装されているため、ソース互換性を維持するためにScalaに実装されていると思います。上記の私の例は、(この特定の場合を除いて)関数へのユーザー入力は関数に定義された型を尊重することを示しています。

+0

また@ rogue-oneありがとう、それは理にかなっている!ちょうど私が正しいと思うので、これはうまくいきます:この特定の '+ 'のインスタンスは' + 'がこのように実装されている片側に' String'を持っています。 Scalaのデザイナーがこの設定で最も賢明であると分かった理由は何であれ、 'Any'は' String'として扱われますか? – patrick

+1

うん、そうです。右側の他のタイプ(「Any + Any」など)ではエラーが発生します。 – Samuel

+2

実際、私はScalaのデザイナーはそれが良いアイデアだと考えているとは思えませんし、JavaはオブジェクトとStringを魔法のように連結することができるので、Javaとの互換性がますます増えていると思います。 – Samuel

1

この文字列連結は、Intではなくすべてのデータ型に対して機能します。インスタンス

scala> case class Elephant(value: String) 
defined class Elephant 

scala> "Hello" + Elephant("elephant") 
res2: String = HelloElephant(elephant) 

ためこれは、タイプ任意の引数を受け付ける(Predef介して)StringOpsで定義さmethod+クラスです。これは暗黙の変換によってStringオブジェクトに利用可能にされ、型がAnyの引数をとるメソッドです。手動ですべてを行う必要はありませんので、利便性 - そう"Hello" + Elephant("elephant")は、それが暗黙の変換(または暗黙的な型キャスト)

  • 目的と呼ばれています"Hello".+(Elephant("elephant"))

  • 1
    • は実際にあります。ほとんどの高水準言語は、文字列、int型、boolsなどの最も使用されるジェネリック医薬品とのことを行います...

    あなたは暗黙的に型を変換するときに使用されるすべてのメソッドを参照してくださいscala.Predefを確認することができ、そしてあなたはそれの制御を取ることができますscala.language.implicitConversionsを使用してください。 Scala Documentationで詳細を読む。

    関連する問題