Merge pull request #409 from Alkarex/patch-1
[mono.git] / mcs / tools / monkeydoc / Lucene.Net / Lucene.Net / Index / TermBuffer.cs
1 /* 
2  * Licensed to the Apache Software Foundation (ASF) under one or more
3  * contributor license agreements.  See the NOTICE file distributed with
4  * this work for additional information regarding copyright ownership.
5  * The ASF licenses this file to You under the Apache License, Version 2.0
6  * (the "License"); you may not use this file except in compliance with
7  * the License.  You may obtain a copy of the License at
8  * 
9  * http://www.apache.org/licenses/LICENSE-2.0
10  * 
11  * Unless required by applicable law or agreed to in writing, software
12  * distributed under the License is distributed on an "AS IS" BASIS,
13  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14  * See the License for the specific language governing permissions and
15  * limitations under the License.
16  */
17
18 using System;
19
20 using IndexInput = Mono.Lucene.Net.Store.IndexInput;
21 using UnicodeUtil = Mono.Lucene.Net.Util.UnicodeUtil;
22
23 namespace Mono.Lucene.Net.Index
24 {
25         
26         sealed class TermBuffer : System.ICloneable
27         {
28                 
29                 private System.String field;
30                 private Term term; // cached
31                 private bool preUTF8Strings; // true if strings are stored in modified UTF8 encoding (LUCENE-510)
32                 private bool dirty; // true if text was set externally (ie not read via UTF8 bytes)
33                 
34                 private UnicodeUtil.UTF16Result text = new UnicodeUtil.UTF16Result();
35                 private UnicodeUtil.UTF8Result bytes = new UnicodeUtil.UTF8Result();
36                 
37                 public int CompareTo(TermBuffer other)
38                 {
39                         if ((System.Object) field == (System.Object) other.field)
40                         // fields are interned
41                                 return CompareChars(text.result, text.length, other.text.result, other.text.length);
42                         else
43                                 return String.CompareOrdinal(field, other.field);
44                 }
45                 
46                 private static int CompareChars(char[] chars1, int len1, char[] chars2, int len2)
47                 {
48                         int end = len1 < len2?len1:len2;
49                         for (int k = 0; k < end; k++)
50                         {
51                                 char c1 = chars1[k];
52                                 char c2 = chars2[k];
53                                 if (c1 != c2)
54                                 {
55                                         return c1 - c2;
56                                 }
57                         }
58                         return len1 - len2;
59                 }
60                 
61                 /// <summary>Call this if the IndexInput passed to {@link #read}
62                 /// stores terms in the "modified UTF8" (pre LUCENE-510)
63                 /// format. 
64                 /// </summary>
65                 internal void  SetPreUTF8Strings()
66                 {
67                         preUTF8Strings = true;
68                 }
69                 
70                 public void  Read(IndexInput input, FieldInfos fieldInfos)
71                 {
72                         this.term = null; // invalidate cache
73                         int start = input.ReadVInt();
74                         int length = input.ReadVInt();
75                         int totalLength = start + length;
76                         if (preUTF8Strings)
77                         {
78                                 text.SetLength(totalLength);
79                                 input.ReadChars(text.result, start, length);
80                         }
81                         else
82                         {
83                                 
84                                 if (dirty)
85                                 {
86                                         // Fully convert all bytes since bytes is dirty
87                                         UnicodeUtil.UTF16toUTF8(text.result, 0, text.length, bytes);
88                                         bytes.SetLength(totalLength);
89                                         input.ReadBytes(bytes.result, start, length);
90                                         UnicodeUtil.UTF8toUTF16(bytes.result, 0, totalLength, text);
91                                         dirty = false;
92                                 }
93                                 else
94                                 {
95                                         // Incrementally convert only the UTF8 bytes that are new:
96                                         bytes.SetLength(totalLength);
97                                         input.ReadBytes(bytes.result, start, length);
98                                         UnicodeUtil.UTF8toUTF16(bytes.result, start, length, text);
99                                 }
100                         }
101                         this.field = fieldInfos.FieldName(input.ReadVInt());
102                 }
103                 
104                 public void  Set(Term term)
105                 {
106                         if (term == null)
107                         {
108                                 Reset();
109                                 return ;
110                         }
111                         System.String termText = term.Text();
112                         int termLen = termText.Length;
113                         text.SetLength(termLen);
114                         SupportClass.TextSupport.GetCharsFromString(termText, 0, termLen, text.result, 0);
115                         dirty = true;
116                         field = term.Field();
117                         this.term = term;
118                 }
119                 
120                 public void  Set(TermBuffer other)
121                 {
122                         text.CopyText(other.text);
123                         dirty = true;
124                         field = other.field;
125                         term = other.term;
126                 }
127                 
128                 public void  Reset()
129                 {
130                         field = null;
131                         text.SetLength(0);
132                         term = null;
133                         dirty = true;
134                 }
135                 
136                 public Term ToTerm()
137                 {
138                         if (field == null)
139                         // unset
140                                 return null;
141                         
142                         if (term == null)
143                                 term = new Term(field, new System.String(text.result, 0, text.length), false);
144                         
145                         return term;
146                 }
147                 
148                 public System.Object Clone()
149                 {
150                         TermBuffer clone = null;
151                         try
152                         {
153                                 clone = (TermBuffer) base.MemberwiseClone();
154                         }
155                         catch (System.Exception e)
156                         {
157                         }
158                         
159                         clone.dirty = true;
160                         clone.bytes = new UnicodeUtil.UTF8Result();
161                         clone.text = new UnicodeUtil.UTF16Result();
162                         clone.text.CopyText(text);
163                         return clone;
164                 }
165         }
166 }