Lucene.Net  3.0.3
Lucene.Net is a port of the Lucene search engine library, written in C# and targeted at .NET runtime users.
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Properties Pages
DocFieldConsumers.cs
Go to the documentation of this file.
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 using System.Collections.Generic;
20 using Lucene.Net.Support;
21 using ArrayUtil = Lucene.Net.Util.ArrayUtil;
22 
23 namespace Lucene.Net.Index
24 {
25 
26  /// <summary>This is just a "splitter" class: it lets you wrap two
27  /// DocFieldConsumer instances as a single consumer.
28  /// </summary>
29 
31  {
32  private void InitBlock()
33  {
34  docFreeList = new PerDoc[1];
35  }
36  internal DocFieldConsumer one;
37  internal DocFieldConsumer two;
38 
40  {
41  InitBlock();
42  this.one = one;
43  this.two = two;
44  }
45 
46  internal override void SetFieldInfos(FieldInfos fieldInfos)
47  {
48  base.SetFieldInfos(fieldInfos);
49  one.SetFieldInfos(fieldInfos);
50  two.SetFieldInfos(fieldInfos);
51  }
52 
53  public override void Flush(IDictionary<DocFieldConsumerPerThread, ICollection<DocFieldConsumerPerField>> threadsAndFields, SegmentWriteState state)
54  {
55 
56  var oneThreadsAndFields = new HashMap<DocFieldConsumerPerThread, ICollection<DocFieldConsumerPerField>>();
57  var twoThreadsAndFields = new HashMap<DocFieldConsumerPerThread, ICollection<DocFieldConsumerPerField>>();
58 
59  foreach(var entry in threadsAndFields)
60  {
62  ICollection<DocFieldConsumerPerField> fields = entry.Value;
63 
64  IEnumerator<DocFieldConsumerPerField> fieldsIt = fields.GetEnumerator();
65  ICollection<DocFieldConsumerPerField> oneFields = new HashSet<DocFieldConsumerPerField>();
66  ICollection<DocFieldConsumerPerField> twoFields = new HashSet<DocFieldConsumerPerField>();
67  while (fieldsIt.MoveNext())
68  {
69  DocFieldConsumersPerField perField = (DocFieldConsumersPerField) fieldsIt.Current;
70  oneFields.Add(perField.one);
71  twoFields.Add(perField.two);
72  }
73 
74  oneThreadsAndFields[perThread.one] = oneFields;
75  twoThreadsAndFields[perThread.two] = twoFields;
76  }
77 
78 
79  one.Flush(oneThreadsAndFields, state);
80  two.Flush(twoThreadsAndFields, state);
81  }
82 
83  public override void CloseDocStore(SegmentWriteState state)
84  {
85  try
86  {
87  one.CloseDocStore(state);
88  }
89  finally
90  {
91  two.CloseDocStore(state);
92  }
93  }
94 
95  public override void Abort()
96  {
97  try
98  {
99  one.Abort();
100  }
101  finally
102  {
103  two.Abort();
104  }
105  }
106 
107  public override bool FreeRAM()
108  {
109  bool any = one.FreeRAM();
110  any |= two.FreeRAM();
111  return any;
112  }
113 
114  public override DocFieldConsumerPerThread AddThread(DocFieldProcessorPerThread docFieldProcessorPerThread)
115  {
116  return new DocFieldConsumersPerThread(docFieldProcessorPerThread, this, one.AddThread(docFieldProcessorPerThread), two.AddThread(docFieldProcessorPerThread));
117  }
118 
119  internal PerDoc[] docFreeList;
120  internal int freeCount;
121  internal int allocCount;
122 
123  internal PerDoc GetPerDoc()
124  {
125  lock (this)
126  {
127  if (freeCount == 0)
128  {
129  allocCount++;
130  if (allocCount > docFreeList.Length)
131  {
132  // Grow our free list up front to make sure we have
133  // enough space to recycle all outstanding PerDoc
134  // instances
135  System.Diagnostics.Debug.Assert(allocCount == 1 + docFreeList.Length);
136  docFreeList = new PerDoc[ArrayUtil.GetNextSize(allocCount)];
137  }
138  return new PerDoc(this);
139  }
140  else
141  return docFreeList[--freeCount];
142  }
143  }
144 
145  internal void FreePerDoc(PerDoc perDoc)
146  {
147  lock (this)
148  {
149  System.Diagnostics.Debug.Assert(freeCount < docFreeList.Length);
150  docFreeList[freeCount++] = perDoc;
151  }
152  }
153 
154  internal class PerDoc:DocumentsWriter.DocWriter
155  {
156  public PerDoc(DocFieldConsumers enclosingInstance)
157  {
158  InitBlock(enclosingInstance);
159  }
160  private void InitBlock(DocFieldConsumers enclosingInstance)
161  {
162  this.enclosingInstance = enclosingInstance;
163  }
164  private DocFieldConsumers enclosingInstance;
165  public DocFieldConsumers Enclosing_Instance
166  {
167  get
168  {
169  return enclosingInstance;
170  }
171 
172  }
173 
174  internal DocumentsWriter.DocWriter one;
175  internal DocumentsWriter.DocWriter two;
176 
177  public override long SizeInBytes()
178  {
179  return one.SizeInBytes() + two.SizeInBytes();
180  }
181 
182  public override void Finish()
183  {
184  try
185  {
186  try
187  {
188  one.Finish();
189  }
190  finally
191  {
192  two.Finish();
193  }
194  }
195  finally
196  {
197  Enclosing_Instance.FreePerDoc(this);
198  }
199  }
200 
201  public override void Abort()
202  {
203  try
204  {
205  try
206  {
207  one.Abort();
208  }
209  finally
210  {
211  two.Abort();
212  }
213  }
214  finally
215  {
216  Enclosing_Instance.FreePerDoc(this);
217  }
218  }
219  }
220  }
221 }