次の方法で共有


Windows Search でのクエリ 処理

このトピックは次のように構成されています。

Windows Search でのクエリは、次の 4 つの方法に基づいています。

  • 高度なクエリ構文 (AQS)
  • 自然クエリ構文 (NQS)
  • 構造化照会言語 (SQL)
  • 構造化クエリ インターフェイス

AQS は、インデックスのクエリを実行したり、検索パラメーターを絞り込んだりするために Windows Search で使用される既定のクエリ構文です。 AQS は主にユーザー向けであり、ユーザーが AQS クエリを作成するために使用できますが、開発者がプログラムでクエリを作成するために使用することもできます。 Windows 7 では、正規の AQS が導入され、プログラムによって AQS クエリを生成するために使用する必要があります。 Windows 7 以降では、AQS 条件が満たされているかどうかに基づいてショートカット メニュー オプションを使用できます。 詳細については、「 コンテキスト メニュー ハンドラーの作成」の「高度なクエリ構文を使用した静的動詞の動的動作の取得」を参照してください。 AQS クエリは、ファイルの種類と呼ばれる特定の種類のファイルに限定できます。 詳細については、「 ファイルの種類と関連付け」を参照してください。 関連するプロパティのリファレンス ドキュメントについては、「 System.Kind」および 「System.KindText」を参照してください。

NQS は、AQS よりも緩やかなクエリ構文であり、人間の言語に似ています。 NQS が既定の AQS ではなく選択されている場合は、Windows Search で NQS を使用してインデックスのクエリを実行できます。

SQL は、クエリを定義するテキスト言語です。 SQL は、さまざまなデータベース テクノロジで一般的です。 Windows Search では SQL を使用し、そのサブセットを実装し、言語に要素を追加して拡張します。 Windows Search SQL は、標準の SQL-92 および SQL-99 データベース クエリ構文を拡張して、テキストベースの検索での有用性を高めます。 Windows Search SQL のすべての機能は、Windows XP および Windows Server 2003 以降の Windows Search と互換性があります。 Windows Search SQL の詳細については、「Windows Search SQL 構文を使用したインデックスのクエリ」および「Windows Search SQL 構文の概要」を参照してください。

構造化クエリ API については、このトピックの後半で説明します。 構造化クエリ API のリファレンス ドキュメントについては、「 インターフェイスのクエリ」を参照してください。 ISearchQueryHelper などのインターフェイスは、一連の入力値から SQL 文字列を構築するのに役立ちます。 このインターフェイスは、AQS ユーザー クエリを Windows Search SQL に変換し、SQL では表すことができるが AQS では表現できないクエリ制限を指定します。 ISearchQueryHelper は、Windows Search データベースに接続するための OLE DB 接続文字列も取得します。

ローカル クエリとリモート クエリ

クエリは、ローカルまたはリモートで実行できます。 FROM 句を使用したローカル クエリを次の例に示します。 ローカル クエリは、ローカル SystemIndex カタログのみを照会します。

FROM SystemIndex

FROM 句を使用したリモート クエリを次の例に示します。 ComputerName を追加すると、前の例がリモート クエリに変換されます。

FROM [<ComputerName>.]SystemIndex

既定では、Windows XP と Windows Server 2003 には Windows Search がインストールされていません。 リモート クエリのサポートを提供するのは、Windows Search 4 (WS4) のみです。 以前のバージョンの Windows デスクトップ検索 (WDS) (3.01 以前など) では、リモート クエリはサポートされていません。 Windows エクスプローラーを使用すると、リモート コンピューターのローカル インデックスに対してファイル システム項目 ("file:" プロトコルによって処理される項目) を照会できます。

リモート クエリで項目を取得するには、項目が次の要件を満たしている必要があります。

  • 汎用名前付け規則 (UNC) パスを使用してアクセスできます。
  • クライアントがアクセスできるリモート コンピューターに存在します。
  • クライアントに読み取りアクセスを許可するようにセキュリティを設定します。

Windows エクスプローラーには、 ネットワークおよび共有センターの "パブリック" 共有 (\\Machine\Public\...)、共有ウィザードで共有されるアイテムの "ユーザー" 共有 (\\Machine\Users\...) など、アイテムを共有するための機能があります。 フォルダーを共有した後は、FROM 句でリモート コンピューターのコンピューター名を指定し、SCOPE 句でリモート コンピューターの UNC パスを指定することで、ローカル インデックスのクエリを実行できます。 FROM 句と SCOPE 句を使用したリモート クエリを次の例に示します。

SELECT System.ItemName FROM MachineName.SystemIndex WHERE SCOPE='file://MachineName/<path>' 

ここで示す例では、SQL を使用します。

構造化クエリ API の概要

構造化クエリは、個々のプロパティに対するクエリのブール値の組み合わせによって情報を検索する機能を提供します。 このトピックでは、最も重要な構造化クエリ API とメソッドの機能について説明します。 構造化クエリ API のリファレンス ドキュメントについては、「 インターフェイスのクエリ」を参照してください。

IQueryParser

IQueryParser::P arse メソッドは、ユーザー入力文字列を解析し、IQuerySolution の形式で解釈を生成します。 そのメソッドの pCustomProperties パラメーターが null でない場合は、 IRichChunk オブジェクトの列挙体です (認識されるカスタム プロパティごとに 1 つ)。 他の IQueryParser メソッドを使用すると、アプリケーションはロケール、スキーマ、ワード ブレーカー、さまざまな種類の名前付きエンティティのハンドラーなど、いくつかのオプションを設定できます。 IQueryParser::GetSchemaProvider は、読み込まれたスキーマを参照するための ISchemaProvider インターフェイスを返します。

IQuerySolution : IConditionFactory

IQuerySolution インターフェイスは、入力文字列の解析結果に関するすべての情報を提供します。 IQuerySolutionIConditionFactory インターフェイスでもあるため、追加の条件ツリー ノードを作成できます。 IQuerySolution::GetQuery メソッドは、解釈の条件ツリーを生成します。 IQuerySolution::GetQuery はセマンティック型も返します。

IConditionFactory

IConditionFactory は、 条件ツリー ノードを作成します。 IConditionFactory::MakeNot簡略化パラメーターがVARIANT_TRUE場合、結果の ICondition は簡略化され、否定ノードである必要はありません。 IConditionFactory::MakeAndOrpSubConditions パラメーターが null でない場合、そのパラメーターは ICondition オブジェクトの列挙体であり、サブツリーになります。IConditionFactory::MakeLeaf は、指定されたプロパティ名、操作、および値を持つリーフ ノードを構築します。 pValueType パラメーターの文字列は、スキーマのセマンティック型の名前である必要があります。 expand パラメーターがVARIANT_TRUEであり、プロパティが仮想の場合、結果として得られる条件ツリーは通常、そのプロパティを定義された構成要素に展開した結果、論理和となります。 null でない場合、 pPropertyNameTermpOperatorTermおよび pValueTerm パラメーターは、プロパティ、操作、および値を示す用語を識別する必要があります。

ICondition : IPersistStream

ICondition インターフェイスは、条件ツリー内の 1 つのノードです。 ノードには、否定ノード、AND ノード、OR ノード、またはリーフ ノードを指定できます。 非リーフ ノード の場合、ICondition::GetSubConditions は サブツリーの列挙を返します。 リーフ ノードの場合、 ICondition の次のメソッドは次の値を返します。

  • GetComparisonInfo は、プロパティ名、操作、および値を返します。
  • GetValueType は、IConditionFactory::MakeLeafpszValueType パラメーターで指定された値のセマンティック型を返します。
  • GetValueNormalization は、値の文字列形式を返します。 (値が既に文字列であった場合、大文字と小文字やアクセントなどに関してこの形式は正規化されます)。
  • GetInputTerms は、 入力文のどの部分がプロパティ名、操作、および値を生成したかについての情報を返します。
  • Clone は、条件ツリーのディープ コピーを返します。

IRichChunk

IRichChunk オブジェクトは、トークン スパンと文字列を識別します。 IRichChunk は、開始位置と長さで識別されるスパン (通常はトークンのスパン) に関する情報を表すユーティリティ インターフェイスです。 このスパン情報には、文字列や VARIANT が含まれます。

IConditionGenerator

IConditionGenerator インターフェイスは、名前付きエンティティ型の認識と条件ツリーの生成を処理するためにアプリケーションによって提供されます。 条件ジェネレーターは、IQueryParser::SetMultiOption を使用して IQueryParser に渡されます IQueryParser は、現在読み込まれているスキーマの ISchemaProvider を使用して IConditionGenerator::Initialize を呼び出します。 これにより、 IConditionGenerator は必要なスキーマ情報を取得できます。 入力文字列を解析するときに、IQueryParser は各 IConditionGenerator::RecognizeNamedEntities メソッドを呼び出して、入力文字列内で認識される名前付きエンティティの出現を報告できるようにします。 IQueryParser は現在のロケールを利用でき、名前付きエンティティのトークンスパンを報告する必要があるため、入力のトークン化を利用する必要があります。

IQueryParser がリーフ ノードを出力しようとしているときに、値のセマンティック型が IConditionGenerator の名前付きエンティティ型と一致する場合、IQueryParser は生成されるノードの情報を使用して IConditionGenerator::GenerateforLeaf を呼び出します。 IConditionGenerator がS_OKを返す場合は、条件ツリー (リーフ ノードである必要はありません) を返し、通常は予防措置として生成される代替文字列解釈を抑制するかどうかを IQueryParser に通知する必要があります。

ITokenCollection

ITokenCollection::NumberOfTokens メソッドはトークンの数を返します。ITokenCollection::GetToken、i番目のトークンに関する情報を返します。 先頭と長さは、入力文字列内の文字位置です。 返されるテキストは、入力文字列の文字をオーバーライドするテキストがある場合にのみ null 以外になります。 これは、たとえば、そのダッシュが否定として解釈されるコンテキストにある場合に、入力文字列のダッシュを NOT でオーバーライドするために使用されます。

INamedEntityCollector

IConditionGenerator は、認識された名前付きエンティティごとに INamedEntityCollector::Add を呼び出します。 スパンはトークン スパンです。 それは常に beginSpan の場合でなければなりません。 beginActual<endActual ? endSpanbeginSpanendSpan は、名前付きエンティティが引用符 (ただし、名前付きエンティティによってカバーされる) などの意味的に重要でないトークンで始まる場合や終わる場合、 beginActualendActual とは異なる場合があります。 値は文字列として表現する必要があり、その後 IConditionGenerator::GenerateForLeaf の呼び出しに表示されます。

ISchemaProvider

ISchemaProvider インターフェイスを使用すると、読み込まれたスキーマでエンティティ (型) とリレーション (プロパティ) を参照できます。 個々のメソッドで実行される内容を次に示します。

  • エンティティは、 スキーマ内のすべてのエンティティ (IEntity) の列挙体を返します。
  • RootEntity は、スキーマのルート エンティティを返します。 フラット スキーマの場合、すべての IQuerySolution のメイン型が返されます。
  • GetEntity は名前でエンティティを検索し、スキーマにそのようなエンティティがない場合はS_FALSEを返します。
  • MetaData、IMetaData インターフェイスの列挙体を返します。

IEntity

IEntity インターフェイスは、名前を持ち、他の型 (プロパティ) との名前付きリレーションシップを多数持ち、基本エンティティから派生する型を表すスキーマ エンティティです。 個々のメソッドで実行される処理を次に示します。

  • IEntity::RelationshipsIRelationship オブジェクトの列挙を返します。このオブジェクトは、この型の送信関係ごとに 1 つずつ返されます。 エンティティの各外向きの関係には名前があります。
  • IEntity::GetRelationship は名前でリレーションシップを検索し、このエンティティにそのようなリレーションシップがない場合はS_FALSEを返します。
  • IEntity::MetaData は、このエンティティのメタデータ ペアごとに 1 つずつ、 IMetaData インターフェイスの列挙を返します。
  • IEntity::D efaultPhrase は、条件ツリーの AQS または NQS 再調整の生成を容易にするために、既定のフレーズを返します。

IRelationship

IRelationship インターフェイスは、ソースと宛先の 2 つのエンティティ間のリレーションシップを表します。 個々のメソッドで実行される内容を次に示します。

  • IRelationship::IsReal は、リレーションシップが実際かどうかを報告します。 たとえば、エンティティ A がエンティティ B から派生し、そこから R という名前のリレーションシップを継承している場合、A には R という名前の独自のリレーションシップが存在する可能性があります。ただし、A と R の間のリレーションシップは B と同じ変換先の型を持つ必要があります。存在する唯一の理由は、B に固有のメタデータを格納することです。このようなBの関係は現実ではないという。
  • IRelationship::Medadata は、このエンティティのメタデータ ペアごとに 1 つずつ、 IMetaData インターフェイスの列挙を返します。
  • IRelationship::D efaultPhrase は、再分類でこのリレーションシップに使用する既定のフレーズを返します。 各リレーションシップには、条件ツリーの AQS または NQS 再調整の生成を容易にするために、それを示す既定の語句があります。

IMetaData

メタデータは、エンティティ、リレーションシップ、またはスキーマ全体にそれぞれ関連付けられているキーと値のペアです。 キーは必ずしも一意であるとは限らないため、メタデータのコレクションはマルチマップと考えることができます。 IMetaData::GetData は、メタデータ ペアのキーと値を取得するために呼び出されます。

クエリのシナリオ

次のシナリオでは、条件ツリーの作成やインデックスのクエリなど、一般的なクエリ シナリオでの Windows Search での構造化クエリ API の使用について説明します。

条件の抽出とクエリの解析

クエリが作成されると、そのスコープは、検索する場所をシステムに指示することによって定義されます。 これにより、検索結果が制限されます。 スコープが定義されると、フィルターが適用され、フィルター セットが返されます。 検索結果は、グラフと同様に、リーフ ノードを含む条件ツリーを構築することによって制限されます。 その後、これらの条件が抽出されます。 条件ツリーはリーフ条件のブール値の組み合わせ (AND、OR、NOT) であり、それぞれが演算を介してプロパティを値に関連付けます。 リーフ ノードは、一部の操作による値に対する 1 つのプロパティに対する制限を表します。

フィルター制限には、制限を記述する論理式が必要です。 この式の定義は、条件ツリーに 1 つのノードを作成するために使用される ICondition インターフェイスから始まります。 次の例では条件が 1 つしかないため、ツリーは変更されません。

    
    [
        object,
        uuid(0FC988D4-C935-4b97-A973-46282EA175C8),
        pointer_default(unique)
    ]
    interface ICondition : IPersistStream
    {
        HRESULT GetConditionType([out, retval] CONDITION_TYPE* pNodeType);
        HRESULT GetSubConditions([in] REFIID riid, [out, retval, iid_is(riid)] void** ppv);
        [local] HRESULT GetComparisonInfo([out, annotation("__deref_opt_out")] LPWSTR *ppszPropertyName, [out, annotation("__out_opt")] CONDITION_OPERATION *pOperation, [out, annotation("__out_opt")] PROPVARIANT *pValue);
        HRESULT GetValueType([out, retval] LPWSTR* ppszValueTypeName);
        HRESULT GetValueNormalization([out, retval] LPWSTR* ppszNormalization);
        [local] HRESULT GetInputTerms([out, annotation("__out_opt")] IRichChunk** ppPropertyTerm, [out, annotation("__out_opt")] IRichChunk** ppOperationTerm, [out, annotation("__out_opt")] IRichChunk** ppValueTerm);
        HRESULT Clone([out, retval] ICondition** ppc);
    };


複数のフィルター条件がある場合、AND および他のブール演算子を使用して 1 つのツリーを実現します。 AND ツリーと OR ツリーは、サブツリーの結合と結合を表します。 NOT ツリーは、その単一サブツリーの否定を表します。 AQS は、ブール演算子を使用して論理式を実現するためのテキスト アプローチを提供し、多くの場合、より簡単です。

次の例では、条件ツリー (ICondition) を視覚的な形式に変換します。 クエリ パーサーは、 IQueryParser インターフェイスを使用して、 ICondition をリッチ テキスト形式 (RTF) クエリ文字列に変換します。 IQueryParser::RestateToString メソッドはクエリ テキストを返しますが、IQueryParser::P arse メソッドは IQuerySolution インターフェイスを生成します。 次の例は、そのすべてを実行する方法を示しています。

    [
        object,
        uuid(2EBDEE67-3505-43f8-9946-EA44ABC8E5B0),
        pointer_default(unique)
    ]
    interface IQueryParser : IUnknown
    {
        HRESULT Parse([in] LPCWSTR pszInputString, [in] IEnumUnknown* pCustomProperties, [out, retval] IQuerySolution** ppSolution);
        HRESULT SetOption([in] STRUCTURED_QUERY_SINGLE_OPTION option, [in] PROPVARIANT const* pOptionValue);
        HRESULT GetOption([in] STRUCTURED_QUERY_SINGLE_OPTION option, [out, retval] PROPVARIANT* pOptionValue);
        HRESULT SetMultiOption([in] STRUCTURED_QUERY_MULTIOPTION option, [in] LPCWSTR pszOptionKey, [in] PROPVARIANT const* pOptionValue);
        HRESULT GetSchemaProvider([out, retval] ISchemaProvider** ppSchemaProvider);
        HRESULT RestateToString([in] ICondition* pCondition, [in] BOOL fUseEnglish, [out] LPWSTR* ppszQueryString);
        HRESULT ParsePropertyValue([in] LPCWSTR pszPropertyName, [in] LPCWSTR pszInputString, [out, retval] IQuerySolution** ppSolution);
        HRESULT RestatePropertyValueToString([in] ICondition* pCondition, [in] BOOL fUseEnglish, [out] LPWSTR* ppszPropertyName, [out] LPWSTR* ppszQueryString);
    };

IQueryParser::P arse の主な入力は、解析するユーザー入力文字列ですが、アプリケーションは(アプリケーション固有の構文から) 入力で認識されたプロパティをクエリ パーサーに通知することもできます。 IQueryParser::Parse の出力は、その解析呼び出しに関連するすべての情報を提供する IQuerySolution です。 ICondition で表される、入力文字列、入力文字列のトークン化方法、解析エラー、解析されたクエリを条件ツリーとして取得するメソッドがあります。 次の例は、...

    [
        object,
        uuid(D6EBC66B-8921-4193-AFDD-A1789FB7FF57),
        pointer_default(unique)
    ]
    interface IQuerySolution : IConditionFactory
    {
        [local] HRESULT GetQuery([out, annotation("__out_opt")] ICondition** ppQueryNode, [out, annotation("__out_opt")] IEntity** ppMainType);
        HRESULT GetErrors([in] REFIID riid, [out, retval, iid_is(riid)] void** ppParseErrors);
        [local] HRESULT GetLexicalData([out, annotation("__deref_opt_out")] LPWSTR* ppszInputString, [out, annotation("__out_opt")] ITokenCollection** ppTokens, [out, annotation("__out_opt")] LCID* pLocale, [out, annotation("__out_opt")] IUnknown** ppWordBreaker);
    }    

    

前の例では、 IQuerySolution::GetQuery は、元のテキスト、テキストを構成するトークン、または条件ツリーなど、クエリに関する情報を取得できました。 返される可能性のあるクエリ値の例を次の表に示します。

返されるクエリ値の例 説明
author:relja OR author:tyler IQueryParser::RestateToString が返すクエリ テキスト
?author?, ?:?, ?relja?, ?OR?, ?author?, ?:?, ?tyler? トークンの分割
未解決の条件ツリー 未解決の条件ツリー

 

返される初期条件ツリーは未解決です。 未解決の条件ツリーでは、 date:yesterdayなどの日付と時刻の参照は絶対時刻に変換されません。 また、仮想プロパティは展開されません。 仮想プロパティは、複数のプロパティの集計として機能するプロパティです。

たとえば、クエリ kind:email from:reljai では、次の未解決および解決済みの条件ツリーが生成されます。 未解決の条件ツリーは左側にあり、解決された条件ツリーは右側にあります。

未解決および解決済みの条件ツリー

解決されたツリーは、 IConditionFactory::Resolve を呼び出すことによって取得できます。 ただし、 SQRO_DONT_RESOLVE_DATETIME を渡すと、日付と時刻は未解決のまま残されます。 未解決の条件ツリーにはクエリに関する情報が含まれているため、未解決の条件ツリーには利点があります。 各リーフ ノードは 、IQuerySolution::GetLexicalData によって返されるトークンを指します。これは、 IRichChunk インターフェイスを使用する場合のプロパティ、演算子、および値に対応します。 次の例は、...

    interface ITokenCollection : IUnknown
    {
        HRESULT NumberOfTokens(ULONG* pCount);
        HRESULT GetToken([in] ULONG i, [out, annotation("__out_opt")] ULONG* pBegin, [out, annotation("__out_opt")] ULONG* pLength, [out, annotation("__deref_opt_out")] LPWSTR* ppsz);
    };

ICondition:: GetInputTerms([out, annotation("__out_opt")] 
IRichChunk** ppPropertyTerm, [out, annotation("__out_opt")] 
IRichChunk** ppOperationTerm, [out, annotation("__out_opt")] 
IRichChunk** ppValueTerm);

    interface IRichChunk : IUnknown
    {
        HRESULT GetData([out, annotation("__out_opt")] ULONG* pFirstPos, [out, annotation("__out_opt")] ULONG* pLength, [out, annotation("__deref_opt_out")] LPWSTR* ppsz, [out, annotation("__out_opt")] PROPVARIANT* pValue);
    }

インデックスのクエリ

インデックスに対してクエリを実行するには、いくつかの方法があります。 SQL に基づくものもあれば、AQS に基づくものもあります。 また、クエリ インターフェイスを使用して、プログラムで Windows Search インデックス のクエリを実行することもできます。 インデックスのクエリには、 ISearchQueryHelperIRowsetPrioritizationIRowsetEvents の 3 つのインターフェイスがあります。 概念については、「 プログラムによるインデックスのクエリ」を参照してください。

ISearchQueryHelper インターフェイスを使用して、インデックスに対してクエリを実行するコンポーネントまたはヘルパー クラスを開発できます。 このインターフェイスは、ISearchCatalogManager (および ISearchCatalogManager2) のヘルパー クラスとして実装され、ISearchCatalogManager::GetQueryHelper を呼び出すことによって取得されます。 概念については、「 ISearchQueryHelper を使用したインデックスのクエリ」を参照してください。

ISearchQueryHelper では、次の機能を使用できます。

  • Windows Search データベースに接続するための OLE DB 接続文字列を取得します。
  • AQS ユーザー クエリを Windows Search SQL に変換します。
  • SQL では表現できますが、AQS では表現できないクエリ制限を指定します。

インデックス作成の優先順位付けイベントと行セット イベントは、Windows 7 以降でサポートされています。 IRowsetPrioritization では、クライアントが特定のクエリで使用されるスコープに通常の優先順位よりも高い値を指定することを要求できるようにする優先順位スタックがあります。 IRowsetEvents は、新しい項目の追加、項目の削除、項目データの変更など、行セット内の項目に対する変更の通知を提供します。 行セット イベント通知を使用すると、既存のクエリの結果が可能な限り最新の状態になります。 概念については、「 Windows 7 でのインデックスの優先順位付けイベントと行セット イベント」を参照してください。

Windows Search でのインデックス作成、クエリ、通知の

インデックス に含まれる内容の

Windows Search でのインデックス作成プロセスの

Windows Search の通知プロセス

URL の書式設定の要件