たとえば、次のようなクラスがある場合
_class Foo {
public int bar;
public Foo(int constructor_var) {
bar = construction_var;
}
public bar_plus_one() {
return bar++;
}
}
Foo foo = new Foo(2);
_
IDEと入力すると_foo.ba
_と入力されますbar
が表示されます。またはString x = foo.bar()
と入力すると、赤い波線が表示されます。 IDEコンテキスト認識になりますか?コードクエリ言語はありますか?それはリフレクションですか?何ですか?
私の質問を少し明確にするために、コードベースをクエリできるようにしたいと考えています。私は(本質的に)_SELECT name FROM methods WHERE signature IS 3 ints
_またはそのようなものを言うことができるツールを探しています。 Intellisenseのような提案を行うために使用するものは何でも、私が見ているべき場所だと思います。
IDEはコードを理解します。コードを解析し、使用可能なクラス、名前、およびすべてのメンバーなど、オートコンプリートに必要なすべての情報を抽出できます。IDEチームはおそらく、この解析を自分で実装するか、コンパイラでプライベートAPIを使用する必要がありました。
コンパイラーは、主な機能と同じことを行います。コンパイラーは、独自に使用するコードベースの表現を構築します。しかし、コンパイラがその情報を外部に公開することはめったにありません。したがって、コードを照会する場合、最も可能性の高いシナリオは、言語の複雑さによっては多くの労力を必要とする独自のパーサーを実装することです。
しかし、あなたの言語がC#であるなら、あなたは幸運です。過去数年間、C#コンパイラチームは Roslynコンパイラ からその情報のみを公開することに力を注いできました。だからSELECT name FROM methods WHERE signature IS 3 ints
は、NuGetパッケージのインポート、コードのロード、LINQクエリの作成( デモンストレーション )と同じくらい簡単です。
非常に高レベルの概要として、IDEにはコンパイラが含まれています。(まあ、コンパイラのmost parts:コードを生成したり最適化したりする必要はありません。残りはすべてあり、字句解析、構文解析、意味解析、型推論、型チェック、マクロ展開、シンボル解決など)
この分析から収集した情報から、IDEはコードのセマンティックモデルを構築し、次にincomplete codeを検出すると十分に使用します高度な魔法それを完了するための最良の方法を理解する(単純なアルゴリズムは可能な限り最短の完了を提供することですが、通常、IDEはそれよりもはるかに洗練されています。)
IDEとコンパイラの間でコードが重複しているため、近年、2つを統合するための取り組みが行われています。例えば。 MicrosoftのRoslyn C#およびVisual Basic.NETコンパイラは、IDEが必要なすべての情報にアクセスできるようにするAPIを使用して明示的に設計されました。同様に、nsc
(新規Scalaコンパイラー)およびdotc
コンパイラー(Scala用)、およびClangコンパイラー(C/C++用)には、IDEに埋め込むためのAPIがあります。
IDEに組み込まれているコンパイラには、従来のバッチコンパイラとは異なる要件があります。非同期、リアクティブ、同時、高速、増分である必要があり、ほとんどの場合、コードの処理は不完全、無効、エラーになります。ただし、これらの要件が矛盾していても、IDEとコンパイラ-が保証されるため、2つを1つにマージすることは理にかなっています。 常にコードを同じように理解している。
反例として、IntelliJ IDEAは独自のコンパイラフレームワークを使用します。IDEAは、プロジェクト全体で単一の言語に依存しないセマンティックグラフを使用します。プロジェクト内でさまざまな言語が使用されます。これにより、さまざまな言語間でコードを自動的に変換したり、ポリグロットプロジェクト内の言語間でリファクタリングしたりするなど、非常に優れた機能を実現できます。 、IntelliJは実際にScalaコンパイラーで正常にコンパイルされるコード、またはその逆のコードに対してエラーを表示します.
Microsoftは Language Server Protocol を開発しました。これは、IDEが標準化されたプロトコルを使用してコンパイラと通信できるようにするAPIです。つまり、LSPを実装するコンパイラは、LSPを実装するevery IDEと自動的に連携し、同様に、LSPを実装するIDEは、コンパイラが対象とするevery languageを自動的にサポートします。 LSPを実装するものが存在します。現在、多くのコンパイラ(tsc
TypeScriptコンパイラ、Idris、Scala)とIDE(Visual Studio Code、Emacs、Vim)がそれを実装しています。
同じように、LSPの成功に基づいて、Scalaコミュニティによる Build Server Protocol を定義するための取り組みが行われました= IDEがビルドツール(SBT、Maven、Gradle、Mill)を抽象化できるようにします。
補遺:私が上で書いたものはすべて、セマンティック機能を備えた "good™️" IDEに適用されます。たとえば、そのWordがそのコンテキストで構文的に合法かどうかに関係なく、現在のファイルのevery Word(コメントからでも)を補完として提供する、非常に多くのより単純なIDEがあります。
IDEはどのようにコンテキスト認識になりますか?
コード補完機能とリファクタリング機能は、通常、ソースコードから 抽象構文ツリー を構築することによって実装されます。 ASTのノードは、変数、演算子、メソッド呼び出しなどを表しています。foo.
、IDEはASTを使用して変数foo
を型Foo
に解決し、リストを表示しますそのタイプのメンバーの。
私のコードベースをクエリできるようにしたいので、私は尋ねています。
これを行う最も簡単な方法は、お気に入りのIDEのプラグインを作成することです。ほとんどのIDEは、プラグインAPIを通じてASTを公開し、既存のインフラストラクチャを活用して新しいコード分析ツールを簡単に構築できるようにします。
IDEは、外部のプラグイン/ツールを使用してオートコンプリートを実行できます。たとえば、vimやCまたはC++では、名前として clang-complete を使用できます。提案するclangの機能を使用して ソースファイルを指定してコード補完を提案する の場合python your IDE(vim、VSCodeなど) 、Atom、Emacs、Sublime、Gedit、...)は、例としてライブラリ jedi のオートコンプリート機能を使用する jedi-vim を使用できます。これらの外部ツールは、 IDE内またはIDEなしで使用できます。