2012-07-24 20 views
25

Mam ~ 1 milionowy dokument produktu Solr index. Mam też całą masę filtrów interfejsu użytkownika, takich jak kategorie, karty, zakresy cen, rozmiary, kolory i niektóre inne filtry.Zapytanie Solr (q) lub zapytanie filtrujące (fq)

Czy to właściwy sposób na zaznaczenie wszystkiego, co (q=\*:\*), podczas gdy wszystkie inne filtry w fq? Przykład:

fq=(catid:90 OR catid:81) AND priceEng:[38 TO 40] AND (size:39 OR size:40 OR size:41 OR size:50 OR size:72) AND (colorGroup:Yellow OR colorGroup:Violet OR colorGroup:Orange ... AND (companyId:81 OR companyId:691 OR companyId:671 OR companyId:628 OR companyId:185 OR companyId:602 OR ... AND endShipDays:[* TO 7])

Dla mnie wszystko od kategorii do companyIds od kolorach i rozmiarach, itp to tylko filtruje. Masz problem z wydajnością w przyszłym rozwoju dzięki temu podejściu? Czy powinienem umieścić niektóre pytania w q, które?

Dziękuję

Odpowiedz

40

Jest to korzystne jest stosowanie filtrów Query Query ponad normalną miarę możliwości.

FilterQuery jest w stanie skorzystać z FilterCache, co stanowiłoby ogromny wzrost wydajności w porównaniu do zapytań.

+0

Cóż, wygląda na to, że prawie wszystko może znajdować się w fq xD. Czy naprawdę dobrze jest mieć q tylko * i fq jako długie zapytanie azz? –

+0

yup ..... ponieważ byłoby to w stanie wykorzystać pamięć podręczną filtru i zwiększyć wydajność. – Jayendra

+0

Ponadto zapytania filtrujące nie mają wpływu na wynik Solr. – javanna

4

Sposób, w jaki używam q i fq. Stosuję wyszukiwanie pełnotekstowe na q i wszystkie filtry na fq. Powiedzmy, że masz pole słowa kluczowego że zamierzasz mieć wyszukiwania pełnotekstowego z pól zdefiniowanych w schemacie z copyField

<copyField source="id" dest="keyword"/> 
<copyField source="category" dest="keyword"/> 
<copyField source="product_name" dest="keyword"/> 
<copyField source="color" dest="keyword"/> 
<copyField source="location" dest="keyword"/> 
<copyField source="price" dest="keyword"/> 
<copyField source="title" dest="keyword"/> 
<copyField source="description" dest="keyword"/> 

Moje zapytanie będzie wyglądać

/select?q={keyword}&fq=category:fashion&fq=location:nyc 

/select?q=jeans&fq=category:fashion&fq=location:nyc 

Jak digitaljoel zasugerował, jeśli musisz wysyłać zapytania do wielu pól, lepiej użyć wielu fq (zobacz powyższe zapytanie) zamiast używać AND i OR z q

Uwaga: W moim przypadku q domyślny dotyczy pola słowa kluczowego jak określono w solrconfig.xml

<requestHandler name="/select" class="solr.SearchHandler"> 
<!-- default values for query parameters can be specified, these 
    will be overridden by parameters in the request 
    --> 
<lst name="defaults"> 
    <str name="echoParams">explicit</str> 
    <int name="rows">10</int> 
    <str name="df">keyword</str> 
</lst> 
6

będę szukać w następujących punktach o polu w celu podjęcia decyzji:

  1. Czy twoje pole ma ustaloną wartość doładowania lub czy w ogóle potrzebujesz punktowania dla tego pola? Jeśli tak, wpisz zapytanie, ponieważ, jak wspomniano powyżej, zapytanie filtrujące nie wykorzystuje wyników.
  2. Czy stan tego pola jest często używany? Jeśli tak - znowu, jak wspomniano wcześniej, filtrowanie pamięci podręcznej może dać ogromną przewagę, ale jeśli nie - może być nawet wolniejsze.
  3. Czy Twój indeks jest stały? Jest to trochę podobne do # 2. Jeśli twój indeks jest często aktualizowany, użycie zapytań filtru może stać się wąskim gardłem, zamiast zwiększać wydajność.

Kilka uwag na temat numeru 3: Z mojego doświadczenia wynika, że ​​miałem duży indeks, który był zapełniany nowymi dokumentami co kilka sekund, a funkcja AutoSoftCommit również była ustawiona na kilka sekund. Podczas miękkiego zatwierdzania został otwarty nowy użytkownik, który unieważnił pamięć podręczną. Co tak naprawdę się działo, współczynnik trafień filtru prawie zawsze wynosił 0. Mogę powiedzieć więcej: Stwierdziłem, że uruchomienie pierwszego filtra jest droższe niż uruchomienie zapytania z tymi wszystkimi warunkami filtrowania przeniesionymi do "q" zamiast "fq". Na przykład moje zapytanie zajęło 1 sekundę z 5 zapytaniami filtracyjnymi (brak trafienia w pamięci podręcznej) i 147 ms, gdy przeniosłem wszystkie warunki "fq" do głównej kwerendy za pomocą "AND". Ale oczywiście, gdy zatrzymałem aktualizacje indeksu, te same zapytania filtrowe zajęły 0 ms, ponieważ użyto pamięci podręcznej. Więc to jest coś do rozważenia.

także kilka innych punktów za pytanie:

  • Staraj się nie używać symboli wieloznacznych w zapytaniu. Znacząco wpływa na wydajność. Dlatego zamiast ":" sugerowałbym użycie jednego warunku, który jest mniejszy-stała-na-żądanie (najbardziej-stała-na-żądanie, które nie potrzebują wyniku, który chcesz umieścić na "fq")
  • Zasięg należy również unikać wyszukiwania (jeśli to możliwe). Ponadto wyszukiwanie zakresów za pomocą symboli wieloznacznych jest jeszcze większe. Chodzi o twoje "endShipDays: [* TO 7]". Na przykład użycie "endShipDays: (1 2 3 4 5 6 7)" byłoby bardziej skuteczne, ale jest to tylko przykład, jest wiele sposobów.

Mam nadzieję, że to pomaga.

Powiązane problemy