#include "util/serialize_value.h"
|
|
#include <algorithm>
|
|
#include <string>
|
|
#include "util/coding.h"
|
|
#include <iostream>
|
|
#include "leveldb/slice.h"
|
|
|
|
namespace leveldb{
|
|
bool compareByFirst(const Field& a, const Field& b) {
|
|
return a.first < b.first; // 按字段名升序排序
|
|
}
|
|
|
|
std::string SerializeValue(const FieldArray& fields){
|
|
FieldArray sortFields = fields;
|
|
std::sort(sortFields.begin(), sortFields.end(), compareByFirst);
|
|
std::string result;
|
|
for (const Field& pairs : sortFields) {
|
|
PutLengthPrefixedSlice(&result, pairs.first);
|
|
PutLengthPrefixedSlice(&result, pairs.second);
|
|
}
|
|
return result;
|
|
}
|
|
|
|
std::string SerializeValue(const FieldSliceArray& fields) {
|
|
using pss = std::pair<Slice,Slice>;
|
|
FieldSliceArray sortFields = fields;
|
|
std::sort(sortFields.begin(), sortFields.end(),
|
|
[&](const pss &lhs, const pss &rhs) {
|
|
return lhs.first.compare(rhs.first);
|
|
});
|
|
std::string result;
|
|
for (const pss& pairs : sortFields) {
|
|
PutLengthPrefixedSlice(&result, pairs.first);
|
|
PutLengthPrefixedSlice(&result, pairs.second);
|
|
}
|
|
return result;
|
|
}
|
|
|
|
FieldArray *ParseValue(const std::string& value_str,FieldArray *fields){
|
|
Slice valueSlice(value_str);
|
|
// FieldArray *res = new FieldArray;
|
|
FieldArray *res = fields;
|
|
Slice nameSlice = Slice();
|
|
Slice valSlice = Slice();
|
|
std::string nameStr;
|
|
std::string valStr;
|
|
while(GetLengthPrefixedSlice(&valueSlice, &nameSlice)){
|
|
nameStr = nameSlice.ToString();
|
|
|
|
if(GetLengthPrefixedSlice(&valueSlice, &valSlice)){
|
|
valStr = valSlice.ToString();
|
|
res->emplace_back(nameStr, valStr);
|
|
} else {
|
|
std::cout << "name and val not match! From ParseValue" << std::endl;
|
|
assert(0);
|
|
}
|
|
nameSlice.clear();
|
|
valSlice.clear();
|
|
}
|
|
return res;
|
|
}
|
|
|
|
void InternalFieldArray::Map() {
|
|
if(isMapped) return;
|
|
for(const Field& pair : fields) {
|
|
map[pair.first] = pair.second;
|
|
}
|
|
isMapped = true;
|
|
}
|
|
|
|
std::string InternalFieldArray::Serialize() {
|
|
std::string result;
|
|
if(isMapped) {
|
|
for(auto pair : map) {
|
|
PutLengthPrefixedSlice(&result, pair.first);
|
|
PutLengthPrefixedSlice(&result, pair.second);
|
|
}
|
|
} else {
|
|
result = SerializeValue(fields);
|
|
}
|
|
return result;
|
|
}
|
|
|
|
bool InternalFieldArray::HasField(const Field& field) {
|
|
if(isMapped) {
|
|
if(map.count(field.first) && map[field.first] == field.second) {
|
|
return true;
|
|
}
|
|
return false;
|
|
}
|
|
return std::find(fields.begin(),fields.end(),field) != fields.end();
|
|
}
|
|
|
|
Slice InternalFieldArray::ValOfName(const std::string &name) {
|
|
if(isMapped) {
|
|
if(map.count(name)) {
|
|
return map[name];
|
|
}
|
|
return Slice();
|
|
}
|
|
|
|
for (auto iter = fields.begin(); iter != fields.end(); iter++){
|
|
if (iter->first == name) {
|
|
return iter->second;
|
|
} else if (iter->first > name) {
|
|
return Slice();
|
|
}
|
|
}
|
|
return Slice();
|
|
}
|
|
|
|
}
|