Haskellは強く型付けされていますか?つまり変数を割り当てた後で、変数のタイプを変更することはできますか?インターネットで答えが見つからないようです。
Static—型はコンパイル時に既知です。 JavaとHaskellには静的型付けがあります。さらにいくつかリストするために、C/C++、C#、Go、Scala、Rustもあります。
静的に型付けされた言語には、型推論がある場合とない場合があります。 Java型推論がほぼ完全に欠けています(しかし、少しずつゆっくり変化しています)); Haskellは完全な型推論を持っています(特定の非常に高度な拡張機能を除いて)。
(型推論は、_var isFoo = true
_と_bool isFoo = ...
_ではなく_Person person = ...
_とvar person = new Person()
のように、最小限の型を手動で宣言するだけでよい場合です。)
Dynamic— Python、JavaScript、Ruby、PHP、Groovy、Clojure、Erlang、ほとんどのLispなど。一部の人は「型なし」と呼んでいます。動的は静的設定内で「エミュレート」できますが、動的に型付けされた言語に外部静的分析ツール/プラグインを追加しない限り、その逆は当てはまりません。一部の言語では、動的と静的が混在しています。
一部の言語では、インポート時に機能するモジュールごとの(段階的)静的型付けを行うこともできます。例: Python + Mypy 、 Typed Clojure 、- JavaScript + Flow 、 PHP + Hack いくつか例を挙げます。
Strong— Cat
として常に処理されることが意図されている値は常にです。それらをDog
のように扱おうとすると、大きな音が発生しますmeeewww
...エラーを意味します。
Weak—これは実質的に2つの類似した明確なものに要約されます。型強制(たとえば_"5"+3
_は_8
_と等しいPHP — or do it!)とメモリの再解釈(たとえば、Cの_(int) someCharValue
_または_(bool) somePtr
_、およびC++でも、C++では_reinterpret_cast
_)を明示的に要求する。したがって、実際にはcoercion-weakとreinterpretation-weakがあり、異なる言語はこれらの方法の1つまたは両方に弱点があります。
興味深いことに、強制は本質的に暗黙的であり、メモリの再解釈は明示的(アセンブリを除く)であるため、弱い型付けは暗黙的および明示的動作で構成されます。たぶんそれが、弱い型付けで2つの異なるサブカテゴリを参照する理由のさらに多くなのです。
4通りの組み合わせが可能な言語と、そのバリエーション/グラデーションがあります。
Haskellはstatic + strong;もちろん、それはunsafeCoerce
を持っているので、静的である可能性があります+少し再解釈が弱い場合がありますが、unsafeCoerce
は、何かが事実であると確信している極端な状況を除いて、非常に嫌われますずっと前に戻って別の方法でストーリー全体を語り直さなければ、コンパイラを説得することはできません。
Cはstatic + weakです。これは、すべてのメモリを元々含まれていなかったもの、つまり弱いものとして自由に再解釈できるためです。ただし、これらの再解釈はすべてタイプチェッカーによって追跡されるため、完全に静的です。しかし、Cは暗黙の強制を行わないため、reinterpret-weakのみです。
Pythonは動的+ほぼ完全に強力です—実行中にコードの特定の行に到達する前にその行に到達する型はありませんが、ランタイムには型が関連付けられており、メモリを再解釈することは不可能です。暗黙の強制も意味のある最小限に保たれるため、Pythonは99.9%強力で0.01%coercion-weakと言うことができます。
PHPとJavaScriptは動的+ほとんど弱い—動的です。つまり、実行して内容をイントロスペクトするまで何も型を持たず、強制がすべて発生します。メソッドと関数を呼び出すだけで、組み込みの操作を使用しない場合を除いて、強制されることを期待することのできない時間と物事。これらの強制は、インターネット上の多くのユーモアの源です。メモリの再解釈がないため、PHPおよびJSはcoercion-weakです。
さらに、静的型付けは型を持つ変数に関するものであり、強い型付けは型を持つ値に関するものであると考える人もいます。これは全体像を理解するために非常に役立つ方法ですが、 true:一部の動的型付け言語では、変数/パラメータに、実行時に適用される型/制約を注釈として付けることもできます。
静的型付けでは、型を持つのは式です。変数に型があるという事実は、大きな式を小さな式から結合する手段として使用される変数の結果にすぎないため、型を持つのは変数自体ではありません。
同様に、動的型付けでは、静的に既知の型を欠くのは変数ではなく、すべて式です。型が欠けている変数は、欠けている型を格納する式の結果にすぎません。
最後の1つのイラスト
動的タイピングでは、すべての猫、犬、そして象(実際には動物園全体)も同じサイズのボックスにパッケージされます。
静的入力では、これらのボックスは異なって見え、中に何が入っているかを示すステッカーが貼られています。
単一のボックスフォームファクターを使用でき、ボックスにラベルを付ける必要がないため、これを好む人もいます。暗黙的に(そして願わくば)タイプの健全性を提供するのは、互いに関するボックスの配置だけです。
ライオンのような匂いがする箱で一時的にトラを輸送し、オオカミやシカと同じように相互接続された箱の配列にクマを置くことで、あらゆる種類のトリックを行うことができるので、それを好む人もいます。
トランスポートボックスのこのようなラベルなしの設定では、ステージパフォーマンスのように、暗黙の配置の不整合を検出するために、考えられるすべての論理シナリオを再生またはシミュレーションする必要があります。一般的に言えば、推論のみに基づいて信頼できる保証を与えることはできません。 (その健全性について部分的な結論を得るためにシステム全体を起動する必要があるアドホックテストケース)
ラベルと、さまざまなラベルのボックスの取り扱い方法に関する明示的なルールにより、自動化/機械化された論理的推論を使用して、ロジスティクスシステムが実行しない、または確実に実行すること(静的検証、正式な証明、またはQuickCheckのような最小の疑似証明)、ロジスティクスチームがクライアントを正しく理解しているかどうかなど、ロジスティクスの一部の側面は、試運転で検証する必要があります。 (統合テスト、受け入れテスト、エンドユーザーの健全性チェック)。
さらに、弱いタイピングでは、犬をスライスしてフランケンシュタイン猫として組み立て直すことができます。彼らがそれを好きかどうか、そして結果が醜いかどうか。 (弱いタイピング)
ただし、ラベルをボックスに追加する場合でも、フランケンシュタインの猫を猫の箱に入れることが重要です。 (静的+弱いタイピング)
強いタイピングでは、犬の箱に猫を入れることはできますが、犬だけが食べるものを与えて屈辱を与えようとするまで、犬のふりをし続けることしかできません。そうなると、大声で叫びます。 、しかしそれまでは、動的なタイピングをしていると、黙ってその場所を受け入れます(静的な世界では、「キティ」と言う前に犬の箱に入れることを拒否します)。
あなたは動的/静的と弱い/強力なタイピングを混同しているようです。
動的型付けまたは静的型付けとは、実行中に変数の型を変更できるかどうかです。
弱い型付けまたは強い型付けとは、関数シグネチャから型エラーを予測できることです。
Haskellは静的型付けと強く型付けされています。
ただし、Haskellには変数などはありません。値を割り当てられたすべての識別子は実行時に変更できないため、動的または静的型付けについて説明しても意味がありません。
編集:しかし、ゴールデンブルが言ったように、それらのタイピングの概念は明確に定義されていません。
強く型付けされています。セクション2.3を参照してください: Haskellが重要な理由
あなたは2つの異なることについて話していると思います。
まず、haskell、およびほとんどの関数型プログラミング(FP)言語には、「変数」という概念がありません。代わりに、「名前」と「値」の概念を使用し、値を名前に「バインド」するだけです。値がバインドされると、別の値を同じ名前にバインドすることはできません。これがFPの重要な機能です。
強い型付けは別のトピックです。はい、haskellは強く型付けされており、ほとんどのFP言語です。強い型付けはFP「型推論」の機能を提供します。これは隠れたバグを排除するために強力ですコンパイル時に、ソースコードのサイズを削減するのに役立ちます。
多分あなたはhaskellをPythonと比較していますか? Pythonも強く型付けされています。haskellとpythonの違いは、「静的型付け」と「動的型付け」です。用語「強い型」の実際の意味「弱いタイプ」はあいまいで曖昧です。これは別の長い話です...