19 using Lucene.Net.Support;
21 using Term = Lucene.Net.Index.Term;
26 namespace Lucene.Net.Search
37 private System.String field;
38 private EquatableList<Term> terms =
new EquatableList<Term>(4);
39 private EquatableList<int> positions =
new EquatableList<int>(4);
40 private int maxPosition = 0;
60 public virtual int Slop
69 public virtual void Add(
Term term)
72 if (positions.Count > 0)
73 position = positions[positions.Count - 1] + 1;
88 public virtual void Add(
Term term,
int position)
92 else if ((System.Object) term.Field != (System.Object) field)
94 throw new System.ArgumentException(
"All phrase terms must be in the same field: " + term);
98 positions.Add(position);
99 if (position > maxPosition)
100 maxPosition = position;
104 public virtual Term[] GetTerms()
106 return terms.ToArray();
110 public virtual int[] GetPositions()
112 int[] result =
new int[positions.Count];
113 for (
int i = 0; i < positions.Count; i++)
114 result[i] = positions[i];
119 private class PhraseWeight:
Weight
121 private void InitBlock(
PhraseQuery enclosingInstance)
123 this.enclosingInstance = enclosingInstance;
130 return enclosingInstance;
135 private float value_Renamed;
137 private float queryNorm;
138 private float queryWeight;
143 InitBlock(enclosingInstance);
144 this.similarity = Enclosing_Instance.GetSimilarity(searcher);
146 idfExp = similarity.IdfExplain(Enclosing_Instance.terms, searcher);
150 public override System.String ToString()
152 return "weight(" + Enclosing_Instance +
")";
157 get {
return Enclosing_Instance; }
160 public override float Value
162 get {
return value_Renamed; }
165 public override float GetSumOfSquaredWeights()
167 queryWeight = idf*Enclosing_Instance.Boost;
168 return queryWeight*queryWeight;
171 public override void Normalize(
float queryNorm)
173 this.queryNorm = queryNorm;
174 queryWeight *= queryNorm;
175 value_Renamed = queryWeight * idf;
180 if (Enclosing_Instance.terms.Count == 0)
185 for (
int i = 0; i < Enclosing_Instance.terms.Count; i++)
187 TermPositions p = reader.TermPositions(Enclosing_Instance.terms[i]);
193 if (Enclosing_Instance.slop == 0)
195 return new ExactPhraseScorer(
this, tps, Enclosing_Instance.GetPositions(), similarity, reader.Norms(Enclosing_Instance.field));
197 return new SloppyPhraseScorer(
this, tps, Enclosing_Instance.GetPositions(), similarity, Enclosing_Instance.slop, reader.Norms(Enclosing_Instance.field));
204 result.Description =
"weight(" +
Query +
" in " + doc +
"), product of:";
206 System.Text.StringBuilder docFreqs =
new System.Text.StringBuilder();
207 System.Text.StringBuilder query =
new System.Text.StringBuilder();
209 docFreqs.Append(idfExp.Explain());
210 for (
int i = 0; i < Enclosing_Instance.terms.Count; i++)
217 Term term = Enclosing_Instance.terms[i];
219 query.Append(term.Text);
227 queryExpl.Description =
"queryWeight(" +
Query +
"), product of:";
230 if (Enclosing_Instance.Boost != 1.0f)
231 queryExpl.AddDetail(boostExpl);
232 queryExpl.AddDetail(idfExpl);
235 queryExpl.AddDetail(queryNormExpl);
237 queryExpl.Value = boostExpl.Value * idfExpl.Value * queryNormExpl.Value;
239 result.AddDetail(queryExpl);
243 fieldExpl.Description =
"fieldWeight(" + Enclosing_Instance.field +
":" + query +
" in " + doc +
"), product of:";
245 PhraseScorer scorer = (PhraseScorer)
Scorer(reader,
true,
false);
251 int d = scorer.Advance(doc);
252 float phraseFreq = (d == doc) ? scorer.CurrentFreq() : 0.0f;
253 tfExplanation.Value = similarity.Tf(phraseFreq);
254 tfExplanation.Description =
"tf(phraseFreq=" + phraseFreq +
")";
256 fieldExpl.AddDetail(tfExplanation);
257 fieldExpl.AddDetail(idfExpl);
260 byte[] fieldNorms = reader.Norms(Enclosing_Instance.field);
261 float fieldNorm = fieldNorms != null?
Similarity.DecodeNorm(fieldNorms[doc]):1.0f;
262 fieldNormExpl.Value = fieldNorm;
263 fieldNormExpl.Description =
"fieldNorm(field=" + Enclosing_Instance.field +
", doc=" + doc +
")";
264 fieldExpl.AddDetail(fieldNormExpl);
266 fieldExpl.Value = tfExplanation.Value * idfExpl.Value * fieldNormExpl.Value;
268 result.AddDetail(fieldExpl);
271 result.Value = queryExpl.Value * fieldExpl.Value;
273 if (queryExpl.Value == 1.0f)
282 if (terms.Count == 1)
285 Term term = terms[0];
287 termQuery.
Boost = Boost;
290 return new PhraseWeight(
this, searcher);
295 public override void ExtractTerms(System.Collections.Generic.ISet<
Term> queryTerms)
297 queryTerms.UnionWith(terms);
301 public override System.String ToString(System.String f)
303 System.Text.StringBuilder buffer =
new System.Text.StringBuilder();
304 if (field != null && !field.Equals(f))
306 buffer.Append(field);
311 System.String[] pieces =
new System.String[maxPosition + 1];
312 for (
int i = 0; i < terms.Count; i++)
314 int pos = positions[i];
315 System.String s = pieces[pos];
322 s = s +
"|" + terms[i].Text;
326 for (
int i = 0; i < pieces.Length; i++)
332 System.String s = pieces[i];
352 return buffer.ToString();
356 public override bool Equals(System.Object o)
361 return (this.Boost == other.
Boost) && (this.slop == other.slop) && this.terms.Equals(other.terms) && this.positions.Equals(other.positions);
365 public override int GetHashCode()
367 return BitConverter.ToInt32(BitConverter.GetBytes(Boost), 0) ^ slop ^ terms.GetHashCode() ^ positions.GetHashCode();