github.com/insionng/yougam@v0.0.0-20170714101924-2bc18d833463/libraries/syndtr/goleveldb/leveldb/testutil/kv.go (about)

     1  // Copyright (c) 2014, Suryandaru Triandana <syndtr@gmail.com>
     2  // All rights reserved.
     3  //
     4  // Use of this source code is governed by a BSD-style license that can be
     5  // found in the LICENSE file.
     6  
     7  package testutil
     8  
     9  import (
    10  	"fmt"
    11  	"math/rand"
    12  	"sort"
    13  	"strings"
    14  
    15  	"github.com/insionng/yougam/libraries/syndtr/goleveldb/leveldb/util"
    16  )
    17  
    18  type KeyValueEntry struct {
    19  	key, value []byte
    20  }
    21  
    22  type KeyValue struct {
    23  	entries []KeyValueEntry
    24  	nbytes  int
    25  }
    26  
    27  func (kv *KeyValue) Put(key, value []byte) {
    28  	if n := len(kv.entries); n > 0 && cmp.Compare(kv.entries[n-1].key, key) >= 0 {
    29  		panic(fmt.Sprintf("Put: keys are not in increasing order: %q, %q", kv.entries[n-1].key, key))
    30  	}
    31  	kv.entries = append(kv.entries, KeyValueEntry{key, value})
    32  	kv.nbytes += len(key) + len(value)
    33  }
    34  
    35  func (kv *KeyValue) PutString(key, value string) {
    36  	kv.Put([]byte(key), []byte(value))
    37  }
    38  
    39  func (kv *KeyValue) PutU(key, value []byte) bool {
    40  	if i, exist := kv.Get(key); !exist {
    41  		if i < kv.Len() {
    42  			kv.entries = append(kv.entries[:i+1], kv.entries[i:]...)
    43  			kv.entries[i] = KeyValueEntry{key, value}
    44  		} else {
    45  			kv.entries = append(kv.entries, KeyValueEntry{key, value})
    46  		}
    47  		kv.nbytes += len(key) + len(value)
    48  		return true
    49  	} else {
    50  		kv.nbytes += len(value) - len(kv.ValueAt(i))
    51  		kv.entries[i].value = value
    52  	}
    53  	return false
    54  }
    55  
    56  func (kv *KeyValue) PutUString(key, value string) bool {
    57  	return kv.PutU([]byte(key), []byte(value))
    58  }
    59  
    60  func (kv *KeyValue) Delete(key []byte) (exist bool, value []byte) {
    61  	i, exist := kv.Get(key)
    62  	if exist {
    63  		value = kv.entries[i].value
    64  		kv.DeleteIndex(i)
    65  	}
    66  	return
    67  }
    68  
    69  func (kv *KeyValue) DeleteIndex(i int) bool {
    70  	if i < kv.Len() {
    71  		kv.nbytes -= len(kv.KeyAt(i)) + len(kv.ValueAt(i))
    72  		kv.entries = append(kv.entries[:i], kv.entries[i+1:]...)
    73  		return true
    74  	}
    75  	return false
    76  }
    77  
    78  func (kv KeyValue) Len() int {
    79  	return len(kv.entries)
    80  }
    81  
    82  func (kv *KeyValue) Size() int {
    83  	return kv.nbytes
    84  }
    85  
    86  func (kv KeyValue) KeyAt(i int) []byte {
    87  	return kv.entries[i].key
    88  }
    89  
    90  func (kv KeyValue) ValueAt(i int) []byte {
    91  	return kv.entries[i].value
    92  }
    93  
    94  func (kv KeyValue) Index(i int) (key, value []byte) {
    95  	if i < 0 || i >= len(kv.entries) {
    96  		panic(fmt.Sprintf("Index #%d: out of range", i))
    97  	}
    98  	return kv.entries[i].key, kv.entries[i].value
    99  }
   100  
   101  func (kv KeyValue) IndexInexact(i int) (key_, key, value []byte) {
   102  	key, value = kv.Index(i)
   103  	var key0 []byte
   104  	var key1 = kv.KeyAt(i)
   105  	if i > 0 {
   106  		key0 = kv.KeyAt(i - 1)
   107  	}
   108  	key_ = BytesSeparator(key0, key1)
   109  	return
   110  }
   111  
   112  func (kv KeyValue) IndexOrNil(i int) (key, value []byte) {
   113  	if i >= 0 && i < len(kv.entries) {
   114  		return kv.entries[i].key, kv.entries[i].value
   115  	}
   116  	return nil, nil
   117  }
   118  
   119  func (kv KeyValue) IndexString(i int) (key, value string) {
   120  	key_, _value := kv.Index(i)
   121  	return string(key_), string(_value)
   122  }
   123  
   124  func (kv KeyValue) Search(key []byte) int {
   125  	return sort.Search(kv.Len(), func(i int) bool {
   126  		return cmp.Compare(kv.KeyAt(i), key) >= 0
   127  	})
   128  }
   129  
   130  func (kv KeyValue) SearchString(key string) int {
   131  	return kv.Search([]byte(key))
   132  }
   133  
   134  func (kv KeyValue) Get(key []byte) (i int, exist bool) {
   135  	i = kv.Search(key)
   136  	if i < kv.Len() && cmp.Compare(kv.KeyAt(i), key) == 0 {
   137  		exist = true
   138  	}
   139  	return
   140  }
   141  
   142  func (kv KeyValue) GetString(key string) (i int, exist bool) {
   143  	return kv.Get([]byte(key))
   144  }
   145  
   146  func (kv KeyValue) Iterate(fn func(i int, key, value []byte)) {
   147  	for i, x := range kv.entries {
   148  		fn(i, x.key, x.value)
   149  	}
   150  }
   151  
   152  func (kv KeyValue) IterateString(fn func(i int, key, value string)) {
   153  	kv.Iterate(func(i int, key, value []byte) {
   154  		fn(i, string(key), string(value))
   155  	})
   156  }
   157  
   158  func (kv KeyValue) IterateShuffled(rnd *rand.Rand, fn func(i int, key, value []byte)) {
   159  	ShuffledIndex(rnd, kv.Len(), 1, func(i int) {
   160  		fn(i, kv.entries[i].key, kv.entries[i].value)
   161  	})
   162  }
   163  
   164  func (kv KeyValue) IterateShuffledString(rnd *rand.Rand, fn func(i int, key, value string)) {
   165  	kv.IterateShuffled(rnd, func(i int, key, value []byte) {
   166  		fn(i, string(key), string(value))
   167  	})
   168  }
   169  
   170  func (kv KeyValue) IterateInexact(fn func(i int, key_, key, value []byte)) {
   171  	for i := range kv.entries {
   172  		key_, key, value := kv.IndexInexact(i)
   173  		fn(i, key_, key, value)
   174  	}
   175  }
   176  
   177  func (kv KeyValue) IterateInexactString(fn func(i int, key_, key, value string)) {
   178  	kv.IterateInexact(func(i int, key_, key, value []byte) {
   179  		fn(i, string(key_), string(key), string(value))
   180  	})
   181  }
   182  
   183  func (kv KeyValue) Clone() KeyValue {
   184  	return KeyValue{append([]KeyValueEntry{}, kv.entries...), kv.nbytes}
   185  }
   186  
   187  func (kv KeyValue) Slice(start, limit int) KeyValue {
   188  	if start < 0 || limit > kv.Len() {
   189  		panic(fmt.Sprintf("Slice %d .. %d: out of range", start, limit))
   190  	} else if limit < start {
   191  		panic(fmt.Sprintf("Slice %d .. %d: invalid range", start, limit))
   192  	}
   193  	return KeyValue{append([]KeyValueEntry{}, kv.entries[start:limit]...), kv.nbytes}
   194  }
   195  
   196  func (kv KeyValue) SliceKey(start, limit []byte) KeyValue {
   197  	start_ := 0
   198  	limit_ := kv.Len()
   199  	if start != nil {
   200  		start_ = kv.Search(start)
   201  	}
   202  	if limit != nil {
   203  		limit_ = kv.Search(limit)
   204  	}
   205  	return kv.Slice(start_, limit_)
   206  }
   207  
   208  func (kv KeyValue) SliceKeyString(start, limit string) KeyValue {
   209  	return kv.SliceKey([]byte(start), []byte(limit))
   210  }
   211  
   212  func (kv KeyValue) SliceRange(r *util.Range) KeyValue {
   213  	if r != nil {
   214  		return kv.SliceKey(r.Start, r.Limit)
   215  	}
   216  	return kv.Clone()
   217  }
   218  
   219  func (kv KeyValue) Range(start, limit int) (r util.Range) {
   220  	if kv.Len() > 0 {
   221  		if start == kv.Len() {
   222  			r.Start = BytesAfter(kv.KeyAt(start - 1))
   223  		} else {
   224  			r.Start = kv.KeyAt(start)
   225  		}
   226  	}
   227  	if limit < kv.Len() {
   228  		r.Limit = kv.KeyAt(limit)
   229  	}
   230  	return
   231  }
   232  
   233  func KeyValue_EmptyKey() *KeyValue {
   234  	kv := &KeyValue{}
   235  	kv.PutString("", "v")
   236  	return kv
   237  }
   238  
   239  func KeyValue_EmptyValue() *KeyValue {
   240  	kv := &KeyValue{}
   241  	kv.PutString("abc", "")
   242  	kv.PutString("abcd", "")
   243  	return kv
   244  }
   245  
   246  func KeyValue_OneKeyValue() *KeyValue {
   247  	kv := &KeyValue{}
   248  	kv.PutString("abc", "v")
   249  	return kv
   250  }
   251  
   252  func KeyValue_BigValue() *KeyValue {
   253  	kv := &KeyValue{}
   254  	kv.PutString("big1", strings.Repeat("1", 200000))
   255  	return kv
   256  }
   257  
   258  func KeyValue_SpecialKey() *KeyValue {
   259  	kv := &KeyValue{}
   260  	kv.PutString("\xff\xff", "v3")
   261  	return kv
   262  }
   263  
   264  func KeyValue_MultipleKeyValue() *KeyValue {
   265  	kv := &KeyValue{}
   266  	kv.PutString("a", "v")
   267  	kv.PutString("aa", "v1")
   268  	kv.PutString("aaa", "v2")
   269  	kv.PutString("aaacccccccccc", "v2")
   270  	kv.PutString("aaaccccccccccd", "v3")
   271  	kv.PutString("aaaccccccccccf", "v4")
   272  	kv.PutString("aaaccccccccccfg", "v5")
   273  	kv.PutString("ab", "v6")
   274  	kv.PutString("abc", "v7")
   275  	kv.PutString("abcd", "v8")
   276  	kv.PutString("accccccccccccccc", "v9")
   277  	kv.PutString("b", "v10")
   278  	kv.PutString("bb", "v11")
   279  	kv.PutString("bc", "v12")
   280  	kv.PutString("c", "v13")
   281  	kv.PutString("c1", "v13")
   282  	kv.PutString("czzzzzzzzzzzzzz", "v14")
   283  	kv.PutString("fffffffffffffff", "v15")
   284  	kv.PutString("g11", "v15")
   285  	kv.PutString("g111", "v15")
   286  	kv.PutString("g111\xff", "v15")
   287  	kv.PutString("zz", "v16")
   288  	kv.PutString("zzzzzzz", "v16")
   289  	kv.PutString("zzzzzzzzzzzzzzzz", "v16")
   290  	return kv
   291  }
   292  
   293  var keymap = []byte("012345678ABCDEFGHIJKLMNOPQRSTUVWXYabcdefghijklmnopqrstuvwxy")
   294  
   295  func KeyValue_Generate(rnd *rand.Rand, n, minlen, maxlen, vminlen, vmaxlen int) *KeyValue {
   296  	if rnd == nil {
   297  		rnd = NewRand()
   298  	}
   299  	if maxlen < minlen {
   300  		panic("max len should >= min len")
   301  	}
   302  
   303  	rrand := func(min, max int) int {
   304  		if min == max {
   305  			return max
   306  		}
   307  		return rnd.Intn(max-min) + min
   308  	}
   309  
   310  	kv := &KeyValue{}
   311  	endC := byte(len(keymap) - 1)
   312  	gen := make([]byte, 0, maxlen)
   313  	for i := 0; i < n; i++ {
   314  		m := rrand(minlen, maxlen)
   315  		last := gen
   316  	retry:
   317  		gen = last[:m]
   318  		if k := len(last); m > k {
   319  			for j := k; j < m; j++ {
   320  				gen[j] = 0
   321  			}
   322  		} else {
   323  			for j := m - 1; j >= 0; j-- {
   324  				c := last[j]
   325  				if c == endC {
   326  					continue
   327  				}
   328  				gen[j] = c + 1
   329  				for j += 1; j < m; j++ {
   330  					gen[j] = 0
   331  				}
   332  				goto ok
   333  			}
   334  			if m < maxlen {
   335  				m++
   336  				goto retry
   337  			}
   338  			panic(fmt.Sprintf("only able to generate %d keys out of %d keys, try increasing max len", kv.Len(), n))
   339  		ok:
   340  		}
   341  		key := make([]byte, m)
   342  		for j := 0; j < m; j++ {
   343  			key[j] = keymap[gen[j]]
   344  		}
   345  		value := make([]byte, rrand(vminlen, vmaxlen))
   346  		for n := copy(value, []byte(fmt.Sprintf("v%d", i))); n < len(value); n++ {
   347  			value[n] = 'x'
   348  		}
   349  		kv.Put(key, value)
   350  	}
   351  	return kv
   352  }