View Javadoc

1   /*
2    *  Licensed to the Apache Software Foundation (ASF) under one
3    *  or more contributor license agreements.  See the NOTICE file
4    *  distributed with this work for additional information
5    *  regarding copyright ownership.  The ASF licenses this file
6    *  to you under the Apache License, Version 2.0 (the
7    *  "License"); you may not use this file except in compliance
8    *  with the License.  You may obtain a copy of the License at
9    *
10   *    http://www.apache.org/licenses/LICENSE-2.0
11   *
12   *  Unless required by applicable law or agreed to in writing,
13   *  software distributed under the License is distributed on an
14   *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
15   *  KIND, either express or implied.  See the License for the
16   *  specific language governing permissions and limitations
17   *  under the License.
18   *
19   */
20  package org.apache.directory.mavibot.btree.serializer;
21  
22  
23  import java.io.IOException;
24  import java.nio.ByteBuffer;
25  import java.util.Comparator;
26  
27  import org.apache.directory.mavibot.btree.comparator.LongArrayComparator;
28  
29  
30  /**
31   * A serializer for a Long[].
32   * 
33   * @author <a href="mailto:labs@labs.apache.org">Mavibot labs Project</a>
34   */
35  public class LongArraySerializer implements ElementSerializer<long[]>
36  {
37      /** The associated comparator */
38      private final Comparator<long[]> comparator;
39  
40  
41      /**
42       * Create a new instance of LongSerializer
43       */
44      public LongArraySerializer()
45      {
46          comparator = new LongArrayComparator();
47      }
48  
49  
50      /**
51       * {@inheritDoc}
52       */
53      public byte[] serialize( long[] element )
54      {
55          int len = -1;
56  
57          if ( element != null )
58          {
59              len = element.length;
60          }
61  
62          byte[] bytes = null;
63  
64          switch ( len )
65          {
66              case 0:
67                  bytes = new byte[4];
68  
69                  bytes[0] = 0x00;
70                  bytes[1] = 0x00;
71                  bytes[2] = 0x00;
72                  bytes[3] = 0x00;
73  
74                  break;
75  
76              case -1:
77                  bytes = new byte[4];
78  
79                  bytes[0] = ( byte ) 0xFF;
80                  bytes[1] = ( byte ) 0xFF;
81                  bytes[2] = ( byte ) 0xFF;
82                  bytes[3] = ( byte ) 0xFF;
83  
84                  break;
85  
86              default:
87                  bytes = new byte[len * 8 + 4];
88                  int pos = 0;
89  
90                  // The number of longs
91                  bytes[pos++] = ( byte ) ( len >>> 24 );
92                  bytes[pos++] = ( byte ) ( len >>> 16 );
93                  bytes[pos++] = ( byte ) ( len >>> 8 );
94                  bytes[pos++] = ( byte ) ( len );
95  
96                  // Serialize the longs now
97                  for ( long value : element )
98                  {
99                      bytes[pos++] = ( byte ) ( value >>> 56 );
100                     bytes[pos++] = ( byte ) ( value >>> 48 );
101                     bytes[pos++] = ( byte ) ( value >>> 40 );
102                     bytes[pos++] = ( byte ) ( value >>> 32 );
103                     bytes[pos++] = ( byte ) ( value >>> 24 );
104                     bytes[pos++] = ( byte ) ( value >>> 16 );
105                     bytes[pos++] = ( byte ) ( value >>> 8 );
106                     bytes[pos++] = ( byte ) ( value );
107                 }
108         }
109 
110         return bytes;
111     }
112 
113 
114     /**
115      * {@inheritDoc}
116      */
117     public long[] deserialize( BufferHandler bufferHandler ) throws IOException
118     {
119         byte[] in = bufferHandler.read( 4 );
120 
121         int len = IntSerializer.deserialize( in );
122 
123         switch ( len )
124         {
125             case 0:
126                 return new long[]
127                     {};
128 
129             case -1:
130                 return null;
131 
132             default:
133                 long[] longs = new long[len];
134 
135                 int pos = 4;
136 
137                 for ( int i = 0; i < len; i++ )
138                 {
139                     longs[i] = ( ( long ) in[pos++] << 56 ) +
140                         ( ( in[pos++] & 0xFFL ) << 48 ) +
141                         ( ( in[pos++] & 0xFFL ) << 40 ) +
142                         ( ( in[pos++] & 0xFFL ) << 32 ) +
143                         ( ( in[pos++] & 0xFFL ) << 24 ) +
144                         ( ( in[pos++] & 0xFFL ) << 16 ) +
145                         ( ( in[pos++] & 0xFFL ) << 8 ) +
146                         ( in[pos++] & 0xFFL );
147                 }
148 
149                 return longs;
150         }
151     }
152 
153 
154     /**
155      * {@inheritDoc}
156      */
157     public long[] deserialize( ByteBuffer buffer ) throws IOException
158     {
159         int len = buffer.getInt();
160 
161         switch ( len )
162         {
163             case 0:
164                 return new long[]
165                     {};
166 
167             case -1:
168                 return null;
169 
170             default:
171                 long[] longs = new long[len];
172 
173                 for ( int i = 0; i < len; i++ )
174                 {
175                     longs[i] = buffer.getLong();
176                 }
177 
178                 return longs;
179         }
180     }
181 
182 
183     /**
184      * {@inheritDoc}
185      */
186     @Override
187     public int compare( long[] type1, long[] type2 )
188     {
189         if ( type1 == type2 )
190         {
191             return 0;
192         }
193 
194         if ( type1 == null )
195         {
196             if ( type2 == null )
197             {
198                 return 0;
199             }
200             else
201             {
202                 return -1;
203             }
204         }
205         else
206         {
207             if ( type2 == null )
208             {
209                 return 1;
210             }
211             else
212             {
213                 if ( type1.length < type2.length )
214                 {
215                     int pos = 0;
216 
217                     for ( long b1 : type1 )
218                     {
219                         long b2 = type2[pos];
220 
221                         if ( b1 == b2 )
222                         {
223                             pos++;
224                         }
225                         else if ( b1 < b2 )
226                         {
227                             return -1;
228                         }
229                         else
230                         {
231                             return 1;
232                         }
233                     }
234 
235                     return 1;
236                 }
237                 else
238                 {
239                     int pos = 0;
240 
241                     for ( long b2 : type2 )
242                     {
243                         long b1 = type1[pos];
244 
245                         if ( b1 == b2 )
246                         {
247                             pos++;
248                         }
249                         else if ( b1 < b2 )
250                         {
251                             return -1;
252                         }
253                         else
254                         {
255                             return 1;
256                         }
257                     }
258 
259                     return -11;
260                 }
261             }
262         }
263     }
264 
265 
266     /**
267      * {@inheritDoc}
268      */
269     @Override
270     public Comparator<long[]> getComparator()
271     {
272         return comparator;
273     }
274 }