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
Payload.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 
20 using TokenStream = Lucene.Net.Analysis.TokenStream;
21 using ArrayUtil = Lucene.Net.Util.ArrayUtil;
22 
23 namespace Lucene.Net.Index
24 {
25 
26  /// <summary> A Payload is metadata that can be stored together with each occurrence
27  /// of a term. This metadata is stored inline in the posting list of the
28  /// specific term.
29  /// <p/>
30  /// To store payloads in the index a <see cref="TokenStream"/> has to be used that
31  /// produces payload data.
32  /// <p/>
33  /// Use <see cref="TermPositions.PayloadLength"/> and <see cref="TermPositions.GetPayload(byte[], int)"/>
34  /// to retrieve the payloads from the index.<br/>
35  ///
36  /// </summary>
37  [Serializable]
38  public class Payload : System.ICloneable
39  {
40  /// <summary>the byte array containing the payload data </summary>
41  protected internal byte[] data;
42 
43  /// <summary>the offset within the byte array </summary>
44  protected internal int internalOffset;
45 
46  /// <summary>the length of the payload data </summary>
47  protected internal int internalLength;
48 
49  /// <summary>Creates an empty payload and does not allocate a byte array. </summary>
50  public Payload()
51  {
52  // nothing to do
53  }
54 
55  /// <summary> Creates a new payload with the the given array as data.
56  /// A reference to the passed-in array is held, i. e. no
57  /// copy is made.
58  ///
59  /// </summary>
60  /// <param name="data">the data of this payload
61  /// </param>
62  public Payload(byte[] data):this(data, 0, data.Length)
63  {
64  }
65 
66  /// <summary> Creates a new payload with the the given array as data.
67  /// A reference to the passed-in array is held, i. e. no
68  /// copy is made.
69  ///
70  /// </summary>
71  /// <param name="data">the data of this payload
72  /// </param>
73  /// <param name="offset">the offset in the data byte array
74  /// </param>
75  /// <param name="length">the length of the data
76  /// </param>
77  public Payload(byte[] data, int offset, int length)
78  {
79  if (offset < 0 || offset + length > data.Length)
80  {
81  throw new System.ArgumentException();
82  }
83  this.data = data;
84  this.internalOffset = offset;
85  this.internalLength = length;
86  }
87 
88  /// <summary> Sets this payloads data.
89  /// A reference to the passed-in array is held, i. e. no
90  /// copy is made.
91  /// </summary>
92  public virtual void SetData(byte[] value, int offset, int length)
93  {
94  this.data = value;
95  this.internalOffset = offset;
96  this.internalLength = length;
97  }
98 
99  /// <summary> Gets or sets a reference to the underlying byte array
100  /// that holds this payloads data. Data is not copied.
101  /// </summary>
102  public virtual void SetData(byte[] value)
103  {
104  SetData(value, 0, value.Length);
105  }
106 
107  /// <summary> Gets or sets a reference to the underlying byte array
108  /// that holds this payloads data. Data is not copied.
109  /// </summary>
110  public virtual byte[] GetData()
111  {
112  return this.data;
113  }
114 
115  /// <summary> Returns the offset in the underlying byte array </summary>
116  public virtual int Offset
117  {
118  get { return this.internalOffset; }
119  }
120 
121  /// <summary> Returns the length of the payload data. </summary>
122  public virtual int Length
123  {
124  get { return this.internalLength; }
125  }
126 
127  /// <summary> Returns the byte at the given index.</summary>
128  public virtual byte ByteAt(int index)
129  {
130  if (0 <= index && index < this.internalLength)
131  {
132  return this.data[this.internalOffset + index];
133  }
134  throw new System. IndexOutOfRangeException("Index of bound " + index);
135  }
136 
137  /// <summary> Allocates a new byte array, copies the payload data into it and returns it. </summary>
138  public virtual byte[] ToByteArray()
139  {
140  byte[] retArray = new byte[this.internalLength];
141  Array.Copy(this.data, this.internalOffset, retArray, 0, this.internalLength);
142  return retArray;
143  }
144 
145  /// <summary> Copies the payload data to a byte array.
146  ///
147  /// </summary>
148  /// <param name="target">the target byte array
149  /// </param>
150  /// <param name="targetOffset">the offset in the target byte array
151  /// </param>
152  public virtual void CopyTo(byte[] target, int targetOffset)
153  {
154  if (this.internalLength > target.Length + targetOffset)
155  {
156  throw new System.IndexOutOfRangeException();
157  }
158  Array.Copy(this.data, this.internalOffset, target, targetOffset, this.internalLength);
159  }
160 
161  /// <summary> Clones this payload by creating a copy of the underlying
162  /// byte array.
163  /// </summary>
164  public virtual System.Object Clone()
165  {
166  try
167  {
168  // Start with a shallow copy of data
169  Payload clone = (Payload) base.MemberwiseClone();
170  // Only copy the part of data that belongs to this Payload
171  if (internalOffset == 0 && internalLength == data.Length)
172  {
173  // It is the whole thing, so just clone it.
174  clone.data = new byte[data.Length];
175  data.CopyTo(clone.data, 0);
176  }
177  else
178  {
179  // Just get the part
180  clone.data = this.ToByteArray();
181  clone.internalOffset = 0;
182  }
183  return clone;
184  }
185  catch (System.Exception e)
186  {
187  throw new System.SystemException(e.Message, e); // shouldn't happen
188  }
189  }
190 
191  public override bool Equals(System.Object obj)
192  {
193  if (obj == this)
194  return true;
195  if (obj is Payload)
196  {
197  Payload other = (Payload) obj;
198  if (internalLength == other.internalLength)
199  {
200  for (int i = 0; i < internalLength; i++)
201  if (data[internalOffset + i] != other.data[other.internalOffset + i])
202  return false;
203  return true;
204  }
205  else
206  return false;
207  }
208  else
209  return false;
210  }
211 
212  public override int GetHashCode()
213  {
214  return ArrayUtil.HashCode(data, internalOffset, internalOffset + internalLength);
215  }
216  }
217 }