OData $filter syntaxis in Azure AI Search

In Azure AI Search geeft de parameter $filter opname- of uitsluitingscriteria op voor het retourneren van overeenkomsten in zoekresultaten. In dit artikel worden de OData-syntaxis van $filter beschreven en vindt u voorbeelden.

Bouw van veldpaden en constanten worden beschreven in het overzicht van de OData-taal in Azure AI Search. Zie Filters in Azure AI Search voor meer informatie over filterscenario's.

Syntaxis

Een filter in de OData-taal is een Boole-expressie, die op zijn beurt een van de verschillende typen expressies kan zijn, zoals wordt weergegeven met het volgende EBNF-formulier (Extended Backus-Naur Form):

boolean_expression ::=
    collection_filter_expression
    | logical_expression
    | comparison_expression
    | boolean_literal
    | boolean_function_call
    | '(' boolean_expression ')'
    | variable

/* This can be a range variable in the case of a lambda, or a field path. */
variable ::= identifier | field_path

Er is ook een interactief syntaxisdiagram beschikbaar:

De typen Boole-expressies zijn:

  • Verzamelingsfilterexpressies met of anyall. Hiermee worden filtercriteria toegepast op verzamelingsvelden. Zie OData-verzamelingsoperators in Azure AI Search voor meer informatie.
  • Logische expressies die andere Boole-expressies combineren met behulp van de operators and, oren not. Zie logische OData-operators in Azure AI Search voor meer informatie.
  • Vergelijkingsexpressies, waarmee velden of bereikvariabelen worden vergeleken met constante waarden met behulp van de operators , ne, , en lege. ltgteq Zie OData-vergelijkingsoperators in Azure AI Search voor meer informatie. Vergelijkingsexpressies worden ook gebruikt om afstanden tussen georuimtelijke coördinaten te vergelijken met behulp van de geo.distance functie. Zie OData geo-ruimtelijke functies in Azure AI Search voor meer informatie.
  • De Booleaanse letterlijke waarden true en false. Deze constanten kunnen soms nuttig zijn bij het programmatisch genereren van filters, maar anders worden ze meestal niet gebruikt in de praktijk.
  • Aanroepen naar Booleaanse functies, waaronder:
  • Veldpaden of bereikvariabelen van het type Edm.Boolean. Als uw index bijvoorbeeld een Booleaans veld heeft aangeroepen IsEnabled en u alle documenten wilt retourneren waarin dit veld zich bevindt true, kan uw filterexpressie alleen de naam IsEnabledzijn.
  • Booleaanse expressies tussen haakjes. Het gebruik van haakjes kan helpen om de volgorde van bewerkingen in een filter expliciet te bepalen. Zie de volgende sectie voor meer informatie over de standaardprioriteit van de OData-operators.

Prioriteit van operator in filters

Als u een filterexpressie schrijft zonder haakjes rond de subexpressies, evalueert Azure AI Search deze op basis van een set operatorprioriteitsregels. Deze regels zijn gebaseerd op welke operators worden gebruikt om subexpressies te combineren. De volgende tabel bevat groepen operators in volgorde van hoogste naar laagste prioriteit:

Groep Operator(s)
Logische operators not
Vergelijkingsoperators eq, , negt, lt, , , gele
Logische operators and
Logische operators or

Een operator die hoger is in de bovenstaande tabel, wordt 'nauwer verbonden' met de operanden dan andere operatoren. Is bijvoorbeeld and een hogere prioriteit dan oren vergelijkingsoperatoren hebben een hogere prioriteit dan een van beide, dus de volgende twee expressies zijn equivalent:

    Rating gt 0 and Rating lt 3 or Rating gt 7 and Rating lt 10
    ((Rating gt 0) and (Rating lt 3)) or ((Rating gt 7) and (Rating lt 10))

De not operator heeft de hoogste prioriteit van alle - zelfs hoger dan de vergelijkingsoperatoren. Daarom kunt u als volgt een filter schrijven:

    not Rating gt 5

U krijgt dit foutbericht:

    Invalid expression: A unary operator with an incompatible type was detected. Found operand type 'Edm.Int32' for operator kind 'Not'.

Deze fout treedt op omdat de operator is gekoppeld aan alleen het veld, dat van het Rating type Edm.Int32is en niet met de volledige vergelijkingsexpressie. De oplossing is om de operand tussen not haakjes te plaatsen:

    not (Rating gt 5)

Beperkingen voor filtergrootte

Er gelden limieten voor de grootte en complexiteit van filterexpressies die u naar Azure AI Search kunt verzenden. De limieten zijn ongeveer gebaseerd op het aantal componenten in uw filterexpressie. Een goede richtlijn is dat als u honderden componenten hebt, u het risico loopt om de limiet te overschrijden. Het is raadzaam om uw toepassing zodanig te ontwerpen dat er geen filters van niet-gebonden grootte worden gegenereerd.

Tip

Het gebruik van de search.in functie in plaats van lange disjunctions van gelijkheidsvergelijkingen kan helpen de limiet van de filtercomponent te voorkomen, omdat een functie-aanroep als één component telt.

Voorbeelden

Zoek alle hotels met ten minste één kamer met een basistarief lager dan $ 200 die zijn geclassificeerd op of hoger dan 4:

    $filter=Rooms/any(room: room/BaseRate lt 200.0) and Rating ge 4

Zoek alle andere hotels dan "Sea View Motel" die sinds 2010 zijn gerenoveerd:

    $filter=HotelName ne 'Sea View Motel' and LastRenovationDate ge 2010-01-01T00:00:00Z

Zoek alle hotels die in 2010 of later zijn gerenoveerd. De letterlijke datum/tijd bevat informatie over de tijdzone voor Pacific Standard Time:

    $filter=LastRenovationDate ge 2010-01-01T00:00:00-08:00

Zoek alle hotels met parkeergelegenheid en waar alle kamers niet-roken zijn:

    $filter=ParkingIncluded and Rooms/all(room: not room/SmokingAllowed)

- OF -

    $filter=ParkingIncluded eq true and Rooms/all(room: room/SmokingAllowed eq false)

Zoek alle hotels die luxe zijn of inclusief parkeren en heb een beoordeling van 5:

    $filter=(Category eq 'Luxury' or ParkingIncluded eq true) and Rating eq 5

Zoek alle hotels met de tag 'wifi' in ten minste één kamer (waar elke kamer tags heeft opgeslagen in een Collection(Edm.String) veld):

    $filter=Rooms/any(room: room/Tags/any(tag: tag eq 'wifi'))

Zoek alle hotels met kamers:

    $filter=Rooms/any()

Zoek alle hotels die geen kamers hebben:

    $filter=not Rooms/any()

Zoek alle hotels binnen 10 kilometer van een bepaald referentiepunt (waar Location is een veld van het type Edm.GeographyPoint):

    $filter=geo.distance(Location, geography'POINT(-122.131577 47.678581)') le 10

Zoek alle hotels in een bepaalde viewport die wordt beschreven als een veelhoek (waar Location is een veld van het type Edm.GeographyPoint). De veelhoek moet gesloten zijn, wat betekent dat de eerste en laatste puntenets hetzelfde moeten zijn. De punten moeten ook worden vermeld in de volgorde van linksom.

    $filter=geo.intersects(Location, geography'POLYGON((-122.031577 47.578581, -122.031577 47.678581, -122.131577 47.678581, -122.031577 47.578581))')

Zoek alle hotels waar het veld Beschrijving null is. Het veld is null als het nooit is ingesteld of als het expliciet is ingesteld op null:

    $filter=Description eq null

Zoek alle hotels met een naam die gelijk is aan 'Sea View motel' of 'Budget hotel'). Deze zinnen bevatten spaties en de spatie is een standaardscheidingsteken. U kunt een alternatief scheidingsteken tussen enkele aanhalingstekens opgeven als de derde tekenreeksparameter:

    $filter=search.in(HotelName, 'Sea View motel,Budget hotel', ',')

Zoek alle hotels met een naam die gelijk is aan 'Sea View motel' of 'Budget hotel' gescheiden door |):

    $filter=search.in(HotelName, 'Sea View motel|Budget hotel', '|')

Zoek alle hotels waar alle kamers de tag 'wifi' of 'tub' hebben:

    $filter=Rooms/any(room: room/Tags/any(tag: search.in(tag, 'wifi, tub')))

Zoek een overeenkomst op zinnen in een verzameling, zoals 'verwarmde handdoekrekken' of 'haardroger inbegrepen' in tags.

    $filter=Rooms/any(room: room/Tags/any(tag: search.in(tag, 'heated towel racks,hairdryer included', ','))

Zoek documenten met het woord 'waterkant'. Deze filterquery is identiek aan een zoekaanvraag met search=waterfront.

    $filter=search.ismatchscoring('waterfront')

Zoek documenten met het woord "hostel" en classificatie groter of gelijk aan 4, of documenten met het woord "motel" en classificatie gelijk aan 5. Deze aanvraag kan niet worden uitgedrukt zonder de search.ismatchscoring functie omdat hiermee zoekopdrachten in volledige tekst worden gecombineerd met filterbewerkingen met behulp van or.

    $filter=search.ismatchscoring('hostel') and rating ge 4 or search.ismatchscoring('motel') and rating eq 5

Zoek documenten zonder het woord 'luxe'.

    $filter=not search.ismatch('luxury')

Zoek documenten met de woordgroep 'oceaanweergave' of classificatie die gelijk is aan 5. De search.ismatchscoring query wordt alleen uitgevoerd op velden HotelName en Description. Documenten die alleen overeenkomen met de tweede component van de disjunction, worden ook geretourneerd -- hotels met Rating gelijk aan 5. Deze documenten worden geretourneerd met score gelijk aan nul om duidelijk te maken dat ze niet overeenkomen met een van de gescoorde delen van de expressie.

    $filter=search.ismatchscoring('"ocean view"', 'Description,HotelName') or Rating eq 5

Zoek hotels waar de termen "hotel" en "airport" niet meer dan vijf woorden uit elkaar liggen in de beschrijving en waar alle kamers niet roken. Deze query maakt gebruik van de volledige Lucene-querytaal.

    $filter=search.ismatch('"hotel airport"~5', 'Description', 'full', 'any') and not Rooms/any(room: room/SmokingAllowed)

Zoek documenten met een woord dat begint met de letters 'lux' in het veld Beschrijving. Deze query maakt gebruik van voorvoegselzoekopdrachten in combinatie met search.ismatch.

    $filter=search.ismatch('lux*', 'Description')

Volgende stappen