fix bugs in api and gclient;
fix bugs in gconsole, pre_var and vstree; support selected pre vars and parallel edges; update both en and ch docs
This commit is contained in:
parent
f25ebcb123
commit
74598bf66e
|
@ -145,7 +145,7 @@ Database::readIDinfo()
|
||||||
fp = fopen(this->free_id_file_entity.c_str(), "r");
|
fp = fopen(this->free_id_file_entity.c_str(), "r");
|
||||||
if (fp == NULL)
|
if (fp == NULL)
|
||||||
{
|
{
|
||||||
cerr << "read entity id info error" << endl;
|
cout << "read entity id info error" << endl;
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
//QUERY:this will reverse the original order, if change?
|
//QUERY:this will reverse the original order, if change?
|
||||||
|
@ -181,7 +181,7 @@ Database::readIDinfo()
|
||||||
fp = fopen(this->free_id_file_literal.c_str(), "r");
|
fp = fopen(this->free_id_file_literal.c_str(), "r");
|
||||||
if (fp == NULL)
|
if (fp == NULL)
|
||||||
{
|
{
|
||||||
cerr << "read literal id info error" << endl;
|
cout << "read literal id info error" << endl;
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
fread(&(this->limitID_literal), sizeof(int), 1, fp);
|
fread(&(this->limitID_literal), sizeof(int), 1, fp);
|
||||||
|
@ -198,7 +198,7 @@ Database::readIDinfo()
|
||||||
fp = fopen(this->free_id_file_predicate.c_str(), "r");
|
fp = fopen(this->free_id_file_predicate.c_str(), "r");
|
||||||
if (fp == NULL)
|
if (fp == NULL)
|
||||||
{
|
{
|
||||||
cerr << "read predicate id info error" << endl;
|
cout << "read predicate id info error" << endl;
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
fread(&(this->limitID_predicate), sizeof(int), 1, fp);
|
fread(&(this->limitID_predicate), sizeof(int), 1, fp);
|
||||||
|
@ -223,7 +223,7 @@ Database::writeIDinfo()
|
||||||
fp = fopen(this->free_id_file_entity.c_str(), "w+");
|
fp = fopen(this->free_id_file_entity.c_str(), "w+");
|
||||||
if (fp == NULL)
|
if (fp == NULL)
|
||||||
{
|
{
|
||||||
cerr << "write entity id info error" << endl;
|
cout << "write entity id info error" << endl;
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
fwrite(&(this->limitID_entity), sizeof(int), 1, fp);
|
fwrite(&(this->limitID_entity), sizeof(int), 1, fp);
|
||||||
|
@ -245,7 +245,7 @@ Database::writeIDinfo()
|
||||||
fp = fopen(this->free_id_file_literal.c_str(), "w+");
|
fp = fopen(this->free_id_file_literal.c_str(), "w+");
|
||||||
if (fp == NULL)
|
if (fp == NULL)
|
||||||
{
|
{
|
||||||
cerr << "write literal id info error" << endl;
|
cout << "write literal id info error" << endl;
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
fwrite(&(this->limitID_literal), sizeof(int), 1, fp);
|
fwrite(&(this->limitID_literal), sizeof(int), 1, fp);
|
||||||
|
@ -263,7 +263,7 @@ Database::writeIDinfo()
|
||||||
fp = fopen(this->free_id_file_predicate.c_str(), "w+");
|
fp = fopen(this->free_id_file_predicate.c_str(), "w+");
|
||||||
if (fp == NULL)
|
if (fp == NULL)
|
||||||
{
|
{
|
||||||
cerr << "write predicate id info error" << endl;
|
cout << "write predicate id info error" << endl;
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
fwrite(&(this->limitID_predicate), sizeof(int), 1, fp);
|
fwrite(&(this->limitID_predicate), sizeof(int), 1, fp);
|
||||||
|
@ -289,7 +289,7 @@ Database::allocEntityID()
|
||||||
t = this->limitID_entity++;
|
t = this->limitID_entity++;
|
||||||
if (this->limitID_entity >= Util::LITERAL_FIRST_ID)
|
if (this->limitID_entity >= Util::LITERAL_FIRST_ID)
|
||||||
{
|
{
|
||||||
cerr << "fail to alloc id for entity" << endl;
|
cout << "fail to alloc id for entity" << endl;
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -330,7 +330,7 @@ Database::allocLiteralID()
|
||||||
t = this->limitID_literal++;
|
t = this->limitID_literal++;
|
||||||
if (this->limitID_literal >= Util::LITERAL_FIRST_ID)
|
if (this->limitID_literal >= Util::LITERAL_FIRST_ID)
|
||||||
{
|
{
|
||||||
cerr << "fail to alloc id for literal" << endl;
|
cout << "fail to alloc id for literal" << endl;
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -371,7 +371,7 @@ Database::allocPredicateID()
|
||||||
t = this->limitID_predicate++;
|
t = this->limitID_predicate++;
|
||||||
if (this->limitID_predicate >= Util::LITERAL_FIRST_ID)
|
if (this->limitID_predicate >= Util::LITERAL_FIRST_ID)
|
||||||
{
|
{
|
||||||
cerr << "fail to alloc id for predicate" << endl;
|
cout << "fail to alloc id for predicate" << endl;
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -408,6 +408,7 @@ Database::release(FILE* fp0)
|
||||||
{
|
{
|
||||||
fprintf(fp0, "begin to delete DB!\n");
|
fprintf(fp0, "begin to delete DB!\n");
|
||||||
fflush(fp0);
|
fflush(fp0);
|
||||||
|
this->vstree->saveTree();
|
||||||
delete this->vstree;
|
delete this->vstree;
|
||||||
fprintf(fp0, "ok to delete vstree!\n");
|
fprintf(fp0, "ok to delete vstree!\n");
|
||||||
fflush(fp0);
|
fflush(fp0);
|
||||||
|
@ -445,6 +446,8 @@ Database::setPreMap()
|
||||||
t = this->kvstore->getPredicateDegree(i);
|
t = this->kvstore->getPredicateDegree(i);
|
||||||
}
|
}
|
||||||
this->pre2num[i] = t;
|
this->pre2num[i] = t;
|
||||||
|
|
||||||
|
//NOTICE:only when pre2num[i]>0 then i is a valid predicate id
|
||||||
if (t > 0)
|
if (t > 0)
|
||||||
{
|
{
|
||||||
valid++;
|
valid++;
|
||||||
|
@ -532,14 +535,14 @@ Database::load()
|
||||||
bool flag = (this->vstree)->loadTree();
|
bool flag = (this->vstree)->loadTree();
|
||||||
if (!flag)
|
if (!flag)
|
||||||
{
|
{
|
||||||
cerr << "load tree error. @Database::load()" << endl;
|
cout << "load tree error. @Database::load()" << endl;
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
flag = this->loadDBInfoFile();
|
flag = this->loadDBInfoFile();
|
||||||
if (!flag)
|
if (!flag)
|
||||||
{
|
{
|
||||||
cerr << "load database info error. @Database::load()" << endl;
|
cout << "load database info error. @Database::load()" << endl;
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -572,6 +575,7 @@ Database::unload()
|
||||||
delete this->entity_buffer;
|
delete this->entity_buffer;
|
||||||
delete this->literal_buffer;
|
delete this->literal_buffer;
|
||||||
|
|
||||||
|
this->vstree->saveTree();
|
||||||
delete this->vstree;
|
delete this->vstree;
|
||||||
this->vstree = NULL;
|
this->vstree = NULL;
|
||||||
delete this->kvstore;
|
delete this->kvstore;
|
||||||
|
@ -579,6 +583,7 @@ Database::unload()
|
||||||
delete this->stringindex;
|
delete this->stringindex;
|
||||||
this->stringindex = NULL;
|
this->stringindex = NULL;
|
||||||
|
|
||||||
|
this->saveDBInfoFile();
|
||||||
this->writeIDinfo();
|
this->writeIDinfo();
|
||||||
this->initIDinfo();
|
this->initIDinfo();
|
||||||
return true;
|
return true;
|
||||||
|
@ -590,10 +595,10 @@ Database::getName()
|
||||||
return this->name;
|
return this->name;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool
|
int
|
||||||
Database::query(const string _query, ResultSet& _result_set, FILE* _fp)
|
Database::query(const string _query, ResultSet& _result_set, FILE* _fp)
|
||||||
{
|
{
|
||||||
GeneralEvaluation general_evaluation(this->vstree, this->kvstore, this->stringindex, this->pre2num);
|
GeneralEvaluation general_evaluation(this->vstree, this->kvstore, this->stringindex, this->pre2num, this->limitID_predicate, this->limitID_literal);
|
||||||
|
|
||||||
long tv_begin = Util::get_cur_time();
|
long tv_begin = Util::get_cur_time();
|
||||||
|
|
||||||
|
@ -602,21 +607,32 @@ Database::query(const string _query, ResultSet& _result_set, FILE* _fp)
|
||||||
long tv_parse = Util::get_cur_time();
|
long tv_parse = Util::get_cur_time();
|
||||||
cout << "after Parsing, used " << (tv_parse - tv_begin) << "ms." << endl;
|
cout << "after Parsing, used " << (tv_parse - tv_begin) << "ms." << endl;
|
||||||
|
|
||||||
|
//TODO:output all results in JSON format, and transformed into string to client
|
||||||
|
//for select, -100 by default, -101 means error
|
||||||
|
//for update, non-negative means true(and the num is updated triples num), -1 means error
|
||||||
|
int success_num = -100;
|
||||||
|
|
||||||
//Query
|
//Query
|
||||||
if (general_evaluation.getQueryTree().getUpdateType() == QueryTree::Not_Update)
|
if (general_evaluation.getQueryTree().getUpdateType() == QueryTree::Not_Update)
|
||||||
{
|
{
|
||||||
general_evaluation.doQuery();
|
bool query_ret = general_evaluation.doQuery();
|
||||||
|
if(!query_ret)
|
||||||
|
{
|
||||||
|
success_num = -101;
|
||||||
|
}
|
||||||
|
|
||||||
long tv_bfget = Util::get_cur_time();
|
long tv_bfget = Util::get_cur_time();
|
||||||
general_evaluation.getFinalResult(_result_set);
|
general_evaluation.getFinalResult(_result_set);
|
||||||
long tv_afget = Util::get_cur_time();
|
long tv_afget = Util::get_cur_time();
|
||||||
cout << "after getFinalResult, used " << (tv_afget - tv_bfget) << "ms." << endl;
|
cout << "after getFinalResult, used " << (tv_afget - tv_bfget) << "ms." << endl;
|
||||||
|
|
||||||
general_evaluation.setNeedOutputAnswer();
|
if(_fp != NULL)
|
||||||
|
general_evaluation.setNeedOutputAnswer();
|
||||||
}
|
}
|
||||||
//Update
|
//Update
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
|
success_num = 0;
|
||||||
TripleWithObjType *update_triple = NULL;
|
TripleWithObjType *update_triple = NULL;
|
||||||
int update_triple_num = 0;
|
int update_triple_num = 0;
|
||||||
|
|
||||||
|
@ -630,18 +646,24 @@ Database::query(const string _query, ResultSet& _result_set, FILE* _fp)
|
||||||
|
|
||||||
for (int i = 0; i < (int)update_pattern.patterns.size(); i++)
|
for (int i = 0; i < (int)update_pattern.patterns.size(); i++)
|
||||||
{
|
{
|
||||||
|
TripleWithObjType::ObjectType object_type = TripleWithObjType::None;
|
||||||
|
if (update_pattern.patterns[i].object.value[0] == '<')
|
||||||
|
object_type = TripleWithObjType::Entity;
|
||||||
|
else
|
||||||
|
object_type = TripleWithObjType::Literal;
|
||||||
|
|
||||||
update_triple[i] = TripleWithObjType(update_pattern.patterns[i].subject.value,
|
update_triple[i] = TripleWithObjType(update_pattern.patterns[i].subject.value,
|
||||||
update_pattern.patterns[i].predicate.value,
|
update_pattern.patterns[i].predicate.value,
|
||||||
update_pattern.patterns[i].object.value);
|
update_pattern.patterns[i].object.value, object_type);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (general_evaluation.getQueryTree().getUpdateType() == QueryTree::Insert_Data)
|
if (general_evaluation.getQueryTree().getUpdateType() == QueryTree::Insert_Data)
|
||||||
{
|
{
|
||||||
insert(update_triple, update_triple_num);
|
success_num = insert(update_triple, update_triple_num);
|
||||||
}
|
}
|
||||||
else if (general_evaluation.getQueryTree().getUpdateType() == QueryTree::Delete_Data)
|
else if (general_evaluation.getQueryTree().getUpdateType() == QueryTree::Delete_Data)
|
||||||
{
|
{
|
||||||
remove(update_triple, update_triple_num);
|
success_num = remove(update_triple, update_triple_num);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else if (general_evaluation.getQueryTree().getUpdateType() == QueryTree::Delete_Where || general_evaluation.getQueryTree().getUpdateType() == QueryTree::Insert_Clause ||
|
else if (general_evaluation.getQueryTree().getUpdateType() == QueryTree::Delete_Where || general_evaluation.getQueryTree().getUpdateType() == QueryTree::Insert_Clause ||
|
||||||
|
@ -653,12 +675,12 @@ Database::query(const string _query, ResultSet& _result_set, FILE* _fp)
|
||||||
if (general_evaluation.getQueryTree().getUpdateType() == QueryTree::Delete_Where || general_evaluation.getQueryTree().getUpdateType() == QueryTree::Delete_Clause || general_evaluation.getQueryTree().getUpdateType() == QueryTree::Modify_Clause)
|
if (general_evaluation.getQueryTree().getUpdateType() == QueryTree::Delete_Where || general_evaluation.getQueryTree().getUpdateType() == QueryTree::Delete_Clause || general_evaluation.getQueryTree().getUpdateType() == QueryTree::Modify_Clause)
|
||||||
{
|
{
|
||||||
general_evaluation.prepareUpdateTriple(general_evaluation.getQueryTree().getDeletePatterns(), update_triple, update_triple_num);
|
general_evaluation.prepareUpdateTriple(general_evaluation.getQueryTree().getDeletePatterns(), update_triple, update_triple_num);
|
||||||
remove(update_triple, update_triple_num);
|
success_num = remove(update_triple, update_triple_num);
|
||||||
}
|
}
|
||||||
if (general_evaluation.getQueryTree().getUpdateType() == QueryTree::Insert_Clause || general_evaluation.getQueryTree().getUpdateType() == QueryTree::Modify_Clause)
|
if (general_evaluation.getQueryTree().getUpdateType() == QueryTree::Insert_Clause || general_evaluation.getQueryTree().getUpdateType() == QueryTree::Modify_Clause)
|
||||||
{
|
{
|
||||||
general_evaluation.prepareUpdateTriple(general_evaluation.getQueryTree().getInsertPatterns(), update_triple, update_triple_num);
|
general_evaluation.prepareUpdateTriple(general_evaluation.getQueryTree().getInsertPatterns(), update_triple, update_triple_num);
|
||||||
insert(update_triple, update_triple_num);
|
success_num = insert(update_triple, update_triple_num);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -673,27 +695,15 @@ Database::query(const string _query, ResultSet& _result_set, FILE* _fp)
|
||||||
{
|
{
|
||||||
cout << "There has answer: " << _result_set.ansNum << endl;
|
cout << "There has answer: " << _result_set.ansNum << endl;
|
||||||
cout << "final result is : " << endl;
|
cout << "final result is : " << endl;
|
||||||
//if (!_result_set.checkUseStream())
|
_result_set.output(_fp);
|
||||||
//{
|
fprintf(_fp, "\n");
|
||||||
|
fflush(_fp); //to empty the output buffer in C (fflush(stdin) not work in GCC)
|
||||||
//cout << _result_set.to_str() << endl;
|
|
||||||
//}
|
|
||||||
//else
|
|
||||||
//{
|
|
||||||
_result_set.output(_fp);
|
|
||||||
//cout<<endl; //empty the buffer;print an empty line
|
|
||||||
fprintf(_fp, "\n");
|
|
||||||
fflush(_fp); //to empty the output buffer in C (fflush(stdin) not work in GCC)
|
|
||||||
//}
|
|
||||||
//_result_set.output(_fp);
|
|
||||||
//fprintf(_fp, "\n");
|
|
||||||
//fflush(_fp); //to empty the output buffer in C (fflush(stdin) not work in GCC)
|
|
||||||
}
|
}
|
||||||
|
|
||||||
#ifdef DEBUG_PRECISE
|
#ifdef DEBUG
|
||||||
fprintf(stderr, "the query function exits!\n");
|
cout<<"query success_num: "<<success_num<<endl;
|
||||||
#endif
|
#endif
|
||||||
return true;
|
return success_num;
|
||||||
}
|
}
|
||||||
|
|
||||||
//NOTICE+QUERY:to save memory for large cases, we can consider building one tree at a time(then release)
|
//NOTICE+QUERY:to save memory for large cases, we can consider building one tree at a time(then release)
|
||||||
|
@ -767,8 +777,8 @@ Database::build(const string& _rdf_file)
|
||||||
cout << "finish build VS-Tree." << endl;
|
cout << "finish build VS-Tree." << endl;
|
||||||
|
|
||||||
//this->vstree->saveTree();
|
//this->vstree->saveTree();
|
||||||
delete this->vstree;
|
//delete this->vstree;
|
||||||
this->vstree = NULL;
|
//this->vstree = NULL;
|
||||||
//sync();
|
//sync();
|
||||||
//cout << "sync vstree" << endl;
|
//cout << "sync vstree" << endl;
|
||||||
|
|
||||||
|
@ -807,7 +817,7 @@ Database::saveDBInfoFile()
|
||||||
|
|
||||||
if (filePtr == NULL)
|
if (filePtr == NULL)
|
||||||
{
|
{
|
||||||
cerr << "error, can not create db info file. @Database::saveDBInfoFile" << endl;
|
cout << "error, can not create db info file. @Database::saveDBInfoFile" << endl;
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -836,7 +846,7 @@ Database::loadDBInfoFile()
|
||||||
|
|
||||||
if (filePtr == NULL)
|
if (filePtr == NULL)
|
||||||
{
|
{
|
||||||
cerr << "error, can not open db info file. @Database::loadDBInfoFile" << endl;
|
cout << "error, can not open db info file. @Database::loadDBInfoFile" << endl;
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -995,9 +1005,9 @@ bool
|
||||||
Database::encodeRDF_new(const string _rdf_file)
|
Database::encodeRDF_new(const string _rdf_file)
|
||||||
{
|
{
|
||||||
#ifdef DEBUG
|
#ifdef DEBUG
|
||||||
//cerr<< "now to log!!!" << endl;
|
//cout<< "now to log!!!" << endl;
|
||||||
Util::logging("In encodeRDF_new");
|
Util::logging("In encodeRDF_new");
|
||||||
//cerr<< "end log!!!" << endl;
|
//cout<< "end log!!!" << endl;
|
||||||
#endif
|
#endif
|
||||||
int** _p_id_tuples = NULL;
|
int** _p_id_tuples = NULL;
|
||||||
int _id_tuples_max = 0;
|
int _id_tuples_max = 0;
|
||||||
|
@ -1080,13 +1090,13 @@ Database::sub2id_pre2id_obj2id_RDFintoSignature(const string _rdf_file, int**& _
|
||||||
}
|
}
|
||||||
|
|
||||||
//Util::logging("finish initial sub2id_pre2id_obj2id");
|
//Util::logging("finish initial sub2id_pre2id_obj2id");
|
||||||
cerr << "finish initial sub2id_pre2id_obj2id" << endl;
|
cout << "finish initial sub2id_pre2id_obj2id" << endl;
|
||||||
|
|
||||||
//BETTER?:close the stdio buffer sync??
|
//BETTER?:close the stdio buffer sync??
|
||||||
ifstream _fin(_rdf_file.c_str());
|
ifstream _fin(_rdf_file.c_str());
|
||||||
if (!_fin)
|
if (!_fin)
|
||||||
{
|
{
|
||||||
cerr << "sub2id&pre2id&obj2id: Fail to open : " << _rdf_file << endl;
|
cout << "sub2id&pre2id&obj2id: Fail to open : " << _rdf_file << endl;
|
||||||
//exit(0);
|
//exit(0);
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
@ -1095,7 +1105,7 @@ Database::sub2id_pre2id_obj2id_RDFintoSignature(const string _rdf_file, int**& _
|
||||||
ofstream _six_tuples_fout(_six_tuples_file.c_str());
|
ofstream _six_tuples_fout(_six_tuples_file.c_str());
|
||||||
if (!_six_tuples_fout)
|
if (!_six_tuples_fout)
|
||||||
{
|
{
|
||||||
cerr << "sub2id&pre2id&obj2id: Fail to open: " << _six_tuples_file << endl;
|
cout << "sub2id&pre2id&obj2id: Fail to open: " << _six_tuples_file << endl;
|
||||||
//exit(0);
|
//exit(0);
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
@ -1287,7 +1297,7 @@ Database::sub2id_pre2id_obj2id_RDFintoSignature(const string _rdf_file, int**& _
|
||||||
string _sig_binary_file = this->getSignatureBFile();
|
string _sig_binary_file = this->getSignatureBFile();
|
||||||
FILE* _sig_fp = fopen(_sig_binary_file.c_str(), "wb");
|
FILE* _sig_fp = fopen(_sig_binary_file.c_str(), "wb");
|
||||||
if (_sig_fp == NULL) {
|
if (_sig_fp == NULL) {
|
||||||
cerr << "Failed to open : " << _sig_binary_file << endl;
|
cout << "Failed to open : " << _sig_binary_file << endl;
|
||||||
}
|
}
|
||||||
|
|
||||||
//EntityBitSet _all_bitset;
|
//EntityBitSet _all_bitset;
|
||||||
|
@ -1321,7 +1331,7 @@ Database::sub2id_pre2id_obj2id_RDFintoSignature(const string _rdf_file, int**& _
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
int
|
bool
|
||||||
Database::insertTriple(const TripleWithObjType& _triple, vector<int>* _vertices, vector<int>* _predicates)
|
Database::insertTriple(const TripleWithObjType& _triple, vector<int>* _vertices, vector<int>* _predicates)
|
||||||
{
|
{
|
||||||
//cout<<endl<<"the new triple is:"<<endl;
|
//cout<<endl<<"the new triple is:"<<endl;
|
||||||
|
@ -1449,7 +1459,7 @@ Database::insertTriple(const TripleWithObjType& _triple, vector<int>* _vertices,
|
||||||
if (_triple_exist)
|
if (_triple_exist)
|
||||||
{
|
{
|
||||||
cout << "this triple already exist" << endl;
|
cout << "this triple already exist" << endl;
|
||||||
return 0;
|
return false;
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
|
@ -1485,7 +1495,7 @@ Database::insertTriple(const TripleWithObjType& _triple, vector<int>* _vertices,
|
||||||
//if new entity then insert it, else update it.
|
//if new entity then insert it, else update it.
|
||||||
if (_is_new_sub)
|
if (_is_new_sub)
|
||||||
{
|
{
|
||||||
//cout<<"to insert: "<<_sub_id<<" "<<this->kvstore->getEntityByID(_sub_id)<<endl;
|
cout<<"to insert: "<<_sub_id<<" "<<this->kvstore->getEntityByID(_sub_id)<<endl;
|
||||||
SigEntry _sig(_sub_id, _sub_entity_bitset);
|
SigEntry _sig(_sub_id, _sub_entity_bitset);
|
||||||
(this->vstree)->insertEntry(_sig);
|
(this->vstree)->insertEntry(_sig);
|
||||||
}
|
}
|
||||||
|
@ -1524,7 +1534,8 @@ Database::insertTriple(const TripleWithObjType& _triple, vector<int>* _vertices,
|
||||||
cout << "update vs_store, used " << (tv_vs_store_end - tv_kv_store_end) << "ms." << endl;
|
cout << "update vs_store, used " << (tv_vs_store_end - tv_kv_store_end) << "ms." << endl;
|
||||||
}
|
}
|
||||||
|
|
||||||
return updateLen;
|
return true;
|
||||||
|
//return updateLen;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool
|
bool
|
||||||
|
@ -1567,8 +1578,8 @@ Database::removeTriple(const TripleWithObjType& _triple, vector<int>* _vertices,
|
||||||
//if subject become an isolated point, remove its corresponding entry
|
//if subject become an isolated point, remove its corresponding entry
|
||||||
if (sub_degree == 0)
|
if (sub_degree == 0)
|
||||||
{
|
{
|
||||||
//cout<<"to remove entry for sub"<<endl;
|
cout<<"to remove entry for sub"<<endl;
|
||||||
//cout<<_sub_id << " "<<this->kvstore->getEntityByID(_sub_id)<<endl;
|
cout<<_sub_id << " "<<this->kvstore->getEntityByID(_sub_id)<<endl;
|
||||||
this->kvstore->subEntityByID(_sub_id);
|
this->kvstore->subEntityByID(_sub_id);
|
||||||
this->kvstore->subIDByEntity(_triple.subject);
|
this->kvstore->subIDByEntity(_triple.subject);
|
||||||
(this->vstree)->removeEntry(_sub_id);
|
(this->vstree)->removeEntry(_sub_id);
|
||||||
|
@ -1680,10 +1691,12 @@ Database::insert(std::string _rdf_file)
|
||||||
|
|
||||||
long tv_load = Util::get_cur_time();
|
long tv_load = Util::get_cur_time();
|
||||||
|
|
||||||
|
int success_num = 0;
|
||||||
|
|
||||||
ifstream _fin(_rdf_file.c_str());
|
ifstream _fin(_rdf_file.c_str());
|
||||||
if (!_fin)
|
if (!_fin)
|
||||||
{
|
{
|
||||||
cerr << "fail to open : " << _rdf_file << ".@insert_test" << endl;
|
cout << "fail to open : " << _rdf_file << ".@insert_test" << endl;
|
||||||
//exit(0);
|
//exit(0);
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
@ -1717,7 +1730,7 @@ Database::insert(std::string _rdf_file)
|
||||||
}
|
}
|
||||||
|
|
||||||
//Process the Triple one by one
|
//Process the Triple one by one
|
||||||
this->insert(triple_array, parse_triple_num);
|
success_num += this->insert(triple_array, parse_triple_num);
|
||||||
//some maybe invalid or duplicate
|
//some maybe invalid or duplicate
|
||||||
//triple_num += parse_triple_num;
|
//triple_num += parse_triple_num;
|
||||||
}
|
}
|
||||||
|
@ -1726,18 +1739,19 @@ Database::insert(std::string _rdf_file)
|
||||||
long tv_insert = Util::get_cur_time();
|
long tv_insert = Util::get_cur_time();
|
||||||
cout << "after insert, used " << (tv_insert - tv_load) << "ms." << endl;
|
cout << "after insert, used " << (tv_insert - tv_load) << "ms." << endl;
|
||||||
//BETTER:update kvstore and vstree separately, to lower the memory cost
|
//BETTER:update kvstore and vstree separately, to lower the memory cost
|
||||||
flag = this->vstree->saveTree();
|
//flag = this->vstree->saveTree();
|
||||||
if (!flag)
|
//if (!flag)
|
||||||
{
|
//{
|
||||||
return false;
|
//return false;
|
||||||
}
|
//}
|
||||||
flag = this->saveDBInfoFile();
|
//flag = this->saveDBInfoFile();
|
||||||
if (!flag)
|
//if (!flag)
|
||||||
{
|
//{
|
||||||
return false;
|
//return false;
|
||||||
}
|
//}
|
||||||
|
|
||||||
cout << "insert rdf triples done." << endl;
|
cout << "insert rdf triples done." << endl;
|
||||||
|
cout<<"inserted triples num: "<<success_num<<endl;
|
||||||
|
|
||||||
//int* list = NULL;
|
//int* list = NULL;
|
||||||
//int len = 0;
|
//int len = 0;
|
||||||
|
@ -1772,11 +1786,12 @@ Database::remove(std::string _rdf_file)
|
||||||
cout << "finish loading" << endl;
|
cout << "finish loading" << endl;
|
||||||
|
|
||||||
long tv_load = Util::get_cur_time();
|
long tv_load = Util::get_cur_time();
|
||||||
|
int success_num = 0;
|
||||||
|
|
||||||
ifstream _fin(_rdf_file.c_str());
|
ifstream _fin(_rdf_file.c_str());
|
||||||
if (!_fin)
|
if (!_fin)
|
||||||
{
|
{
|
||||||
cerr << "fail to open : " << _rdf_file << ".@remove_test" << endl;
|
cout << "fail to open : " << _rdf_file << ".@remove_test" << endl;
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1805,7 +1820,7 @@ Database::remove(std::string _rdf_file)
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
this->remove(triple_array, parse_triple_num);
|
success_num += this->remove(triple_array, parse_triple_num);
|
||||||
//some maybe invalid or duplicate
|
//some maybe invalid or duplicate
|
||||||
//triple_num -= parse_triple_num;
|
//triple_num -= parse_triple_num;
|
||||||
}
|
}
|
||||||
|
@ -1817,31 +1832,33 @@ Database::remove(std::string _rdf_file)
|
||||||
long tv_remove = Util::get_cur_time();
|
long tv_remove = Util::get_cur_time();
|
||||||
cout << "after remove, used " << (tv_remove - tv_load) << "ms." << endl;
|
cout << "after remove, used " << (tv_remove - tv_load) << "ms." << endl;
|
||||||
|
|
||||||
flag = this->vstree->saveTree();
|
//flag = this->vstree->saveTree();
|
||||||
if (!flag)
|
//if (!flag)
|
||||||
{
|
//{
|
||||||
return false;
|
//return false;
|
||||||
}
|
//}
|
||||||
flag = this->saveDBInfoFile();
|
//flag = this->saveDBInfoFile();
|
||||||
if (!flag)
|
//if (!flag)
|
||||||
{
|
//{
|
||||||
return false;
|
//return false;
|
||||||
}
|
//}
|
||||||
|
|
||||||
cout << "remove rdf triples done." << endl;
|
cout << "remove rdf triples done." << endl;
|
||||||
|
cout<<"removed triples num: "<<success_num<<endl;
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool
|
int
|
||||||
Database::insert(const TripleWithObjType* _triples, int _triple_num)
|
Database::insert(const TripleWithObjType* _triples, int _triple_num)
|
||||||
{
|
{
|
||||||
vector<int> vertices, predicates;
|
vector<int> vertices, predicates;
|
||||||
|
int valid_num = 0;
|
||||||
|
|
||||||
#ifdef USE_GROUP_INSERT
|
#ifdef USE_GROUP_INSERT
|
||||||
//NOTICE:this is called by insert(file) or query()(but can not be too large),
|
//NOTICE:this is called by insert(file) or query()(but can not be too large),
|
||||||
//assume that db is loaded already
|
//assume that db is loaded already
|
||||||
int** id_tuples = new int*[_triple_num];
|
int** id_tuples = new int*[_triple_num];
|
||||||
int valid_num = 0;
|
|
||||||
int i = 0;
|
int i = 0;
|
||||||
//for(i = 0; i < _triple_num; ++i)
|
//for(i = 0; i < _triple_num; ++i)
|
||||||
//{
|
//{
|
||||||
|
@ -1939,10 +1956,14 @@ Database::insert(const TripleWithObjType* _triples, int _triple_num)
|
||||||
}
|
}
|
||||||
if (triple_exist)
|
if (triple_exist)
|
||||||
{
|
{
|
||||||
|
#ifdef DEBUG
|
||||||
cout << "this triple exist" << endl;
|
cout << "this triple exist" << endl;
|
||||||
|
#endif
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
#ifdef DEBUG
|
||||||
cout << "this triple not exist" << endl;
|
cout << "this triple not exist" << endl;
|
||||||
|
#endif
|
||||||
|
|
||||||
id_tuples[valid_num] = new int[3];
|
id_tuples[valid_num] = new int[3];
|
||||||
id_tuples[valid_num][0] = subid;
|
id_tuples[valid_num][0] = subid;
|
||||||
|
@ -2011,9 +2032,11 @@ Database::insert(const TripleWithObjType* _triples, int _triple_num)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#ifdef DEBUG
|
||||||
cout << "old sigmap size: " << old_sigmap.size() << endl;
|
cout << "old sigmap size: " << old_sigmap.size() << endl;
|
||||||
cout << "new sigmap size: " << new_sigmap.size() << endl;
|
cout << "new sigmap size: " << new_sigmap.size() << endl;
|
||||||
cout << "valid num: " << valid_num << endl;
|
cout << "valid num: " << valid_num << endl;
|
||||||
|
#endif
|
||||||
|
|
||||||
//NOTICE:need to sort and remove duplicates, update the valid num
|
//NOTICE:need to sort and remove duplicates, update the valid num
|
||||||
//Notice that duplicates in a group can csuse problem
|
//Notice that duplicates in a group can csuse problem
|
||||||
|
@ -2027,7 +2050,9 @@ Database::insert(const TripleWithObjType* _triples, int _triple_num)
|
||||||
//
|
//
|
||||||
//spo cmp: s2p s2o s2po sp2o
|
//spo cmp: s2p s2o s2po sp2o
|
||||||
{
|
{
|
||||||
|
#ifdef DEBUG
|
||||||
cout << "INSRET PROCESS: to spo cmp and update" << endl;
|
cout << "INSRET PROCESS: to spo cmp and update" << endl;
|
||||||
|
#endif
|
||||||
qsort(id_tuples, valid_num, sizeof(int*), KVstore::_spo_cmp);
|
qsort(id_tuples, valid_num, sizeof(int*), KVstore::_spo_cmp);
|
||||||
|
|
||||||
//To remove duplicates
|
//To remove duplicates
|
||||||
|
@ -2080,7 +2105,9 @@ Database::insert(const TripleWithObjType* _triples, int _triple_num)
|
||||||
|
|
||||||
if (_sub_pre_change)
|
if (_sub_pre_change)
|
||||||
{
|
{
|
||||||
|
#ifdef DEBUG
|
||||||
cout << "update sp2o: " << _sub_id << " " << _pre_id << " " << oidlist_sp.size() << endl;
|
cout << "update sp2o: " << _sub_id << " " << _pre_id << " " << oidlist_sp.size() << endl;
|
||||||
|
#endif
|
||||||
cout << this->kvstore->getEntityByID(_sub_id) << endl;
|
cout << this->kvstore->getEntityByID(_sub_id) << endl;
|
||||||
cout << this->kvstore->getPredicateByID(_pre_id) << endl;
|
cout << this->kvstore->getPredicateByID(_pre_id) << endl;
|
||||||
//this->kvstore->updateInsert_sp2o(_sub_id, _pre_id, oidlist_sp);
|
//this->kvstore->updateInsert_sp2o(_sub_id, _pre_id, oidlist_sp);
|
||||||
|
@ -2089,26 +2116,36 @@ Database::insert(const TripleWithObjType* _triples, int _triple_num)
|
||||||
|
|
||||||
if (_sub_change)
|
if (_sub_change)
|
||||||
{
|
{
|
||||||
|
#ifdef DEBUG
|
||||||
cout << "update s2p: " << _sub_id << " " << pidlist_s.size() << endl;
|
cout << "update s2p: " << _sub_id << " " << pidlist_s.size() << endl;
|
||||||
|
#endif
|
||||||
//this->kvstore->updateInsert_s2p(_sub_id, pidlist_s);
|
//this->kvstore->updateInsert_s2p(_sub_id, pidlist_s);
|
||||||
pidlist_s.clear();
|
pidlist_s.clear();
|
||||||
|
|
||||||
|
#ifdef DEBUG
|
||||||
cout << "update s2po: " << _sub_id << " " << pidoidlist_s.size() << endl;
|
cout << "update s2po: " << _sub_id << " " << pidoidlist_s.size() << endl;
|
||||||
|
#endif
|
||||||
this->kvstore->updateInsert_s2values(_sub_id, pidoidlist_s);
|
this->kvstore->updateInsert_s2values(_sub_id, pidoidlist_s);
|
||||||
pidoidlist_s.clear();
|
pidoidlist_s.clear();
|
||||||
|
|
||||||
|
#ifdef DEBUG
|
||||||
cout << "update s2o: " << _sub_id << " " << oidlist_s.size() << endl;
|
cout << "update s2o: " << _sub_id << " " << oidlist_s.size() << endl;
|
||||||
|
#endif
|
||||||
sort(oidlist_s.begin(), oidlist_s.end());
|
sort(oidlist_s.begin(), oidlist_s.end());
|
||||||
//this->kvstore->updateInsert_s2o(_sub_id, oidlist_s);
|
//this->kvstore->updateInsert_s2o(_sub_id, oidlist_s);
|
||||||
oidlist_s.clear();
|
oidlist_s.clear();
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
cerr << "INSERT PROCESS: OUT s2po..." << endl;
|
#ifdef DEBUG
|
||||||
|
cout << "INSERT PROCESS: OUT s2po..." << endl;
|
||||||
|
#endif
|
||||||
}
|
}
|
||||||
//ops cmp: o2p o2s o2ps op2s
|
//ops cmp: o2p o2s o2ps op2s
|
||||||
{
|
{
|
||||||
|
#ifdef DEBUG
|
||||||
cout << "INSRET PROCESS: to ops cmp and update" << endl;
|
cout << "INSRET PROCESS: to ops cmp and update" << endl;
|
||||||
|
#endif
|
||||||
qsort(id_tuples, valid_num, sizeof(int**), KVstore::_ops_cmp);
|
qsort(id_tuples, valid_num, sizeof(int**), KVstore::_ops_cmp);
|
||||||
vector<int> sidlist_o;
|
vector<int> sidlist_o;
|
||||||
vector<int> sidlist_op;
|
vector<int> sidlist_op;
|
||||||
|
@ -2138,33 +2175,45 @@ Database::insert(const TripleWithObjType* _triples, int _triple_num)
|
||||||
|
|
||||||
if (_obj_pre_change)
|
if (_obj_pre_change)
|
||||||
{
|
{
|
||||||
|
#ifdef DEBUG
|
||||||
cout << "update op2s: " << _obj_id << " " << _pre_id << " " << sidlist_op.size() << endl;
|
cout << "update op2s: " << _obj_id << " " << _pre_id << " " << sidlist_op.size() << endl;
|
||||||
|
#endif
|
||||||
//this->kvstore->updateInsert_op2s(_obj_id, _pre_id, sidlist_op);
|
//this->kvstore->updateInsert_op2s(_obj_id, _pre_id, sidlist_op);
|
||||||
sidlist_op.clear();
|
sidlist_op.clear();
|
||||||
}
|
}
|
||||||
|
|
||||||
if (_obj_change)
|
if (_obj_change)
|
||||||
{
|
{
|
||||||
|
#ifdef DEBUG
|
||||||
cout << "update o2s: " << _obj_id << " " << sidlist_o.size() << endl;
|
cout << "update o2s: " << _obj_id << " " << sidlist_o.size() << endl;
|
||||||
|
#endif
|
||||||
sort(sidlist_o.begin(), sidlist_o.end());
|
sort(sidlist_o.begin(), sidlist_o.end());
|
||||||
//this->kvstore->updateInsert_o2s(_obj_id, sidlist_o);
|
//this->kvstore->updateInsert_o2s(_obj_id, sidlist_o);
|
||||||
sidlist_o.clear();
|
sidlist_o.clear();
|
||||||
|
|
||||||
|
#ifdef DEBUG
|
||||||
cout << "update o2ps: " << _obj_id << " " << pidsidlist_o.size() << endl;
|
cout << "update o2ps: " << _obj_id << " " << pidsidlist_o.size() << endl;
|
||||||
|
#endif
|
||||||
this->kvstore->updateInsert_o2values(_obj_id, pidsidlist_o);
|
this->kvstore->updateInsert_o2values(_obj_id, pidsidlist_o);
|
||||||
pidsidlist_o.clear();
|
pidsidlist_o.clear();
|
||||||
|
|
||||||
|
#ifdef DEBUG
|
||||||
cout << "update o2p: " << _obj_id << " " << pidlist_o.size() << endl;
|
cout << "update o2p: " << _obj_id << " " << pidlist_o.size() << endl;
|
||||||
|
#endif
|
||||||
//this->kvstore->updateInsert_o2p(_obj_id, pidlist_o);
|
//this->kvstore->updateInsert_o2p(_obj_id, pidlist_o);
|
||||||
pidlist_o.clear();
|
pidlist_o.clear();
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
cerr << "INSERT PROCESS: OUT o2ps..." << endl;
|
#ifdef DEBUG
|
||||||
|
cout << "INSERT PROCESS: OUT o2ps..." << endl;
|
||||||
|
#endif
|
||||||
}
|
}
|
||||||
//pso cmp: p2s p2o p2so
|
//pso cmp: p2s p2o p2so
|
||||||
{
|
{
|
||||||
|
#ifdef DEBUG
|
||||||
cout << "INSRET PROCESS: to pso cmp and update" << endl;
|
cout << "INSRET PROCESS: to pso cmp and update" << endl;
|
||||||
|
#endif
|
||||||
qsort(id_tuples, valid_num, sizeof(int*), KVstore::_pso_cmp);
|
qsort(id_tuples, valid_num, sizeof(int*), KVstore::_pso_cmp);
|
||||||
vector<int> sidlist_p;
|
vector<int> sidlist_p;
|
||||||
vector<int> oidlist_p;
|
vector<int> oidlist_p;
|
||||||
|
@ -2192,21 +2241,29 @@ Database::insert(const TripleWithObjType* _triples, int _triple_num)
|
||||||
|
|
||||||
if (_pre_change)
|
if (_pre_change)
|
||||||
{
|
{
|
||||||
|
#ifdef DEBUG
|
||||||
cout << "update p2s: " << _pre_id << " " << sidlist_p.size() << endl;
|
cout << "update p2s: " << _pre_id << " " << sidlist_p.size() << endl;
|
||||||
|
#endif
|
||||||
//this->kvstore->updateInsert_p2s(_pre_id, sidlist_p);
|
//this->kvstore->updateInsert_p2s(_pre_id, sidlist_p);
|
||||||
sidlist_p.clear();
|
sidlist_p.clear();
|
||||||
|
|
||||||
|
#ifdef DEBUG
|
||||||
cout << "update p2o: " << _pre_id << " " << oidlist_p.size() << endl;
|
cout << "update p2o: " << _pre_id << " " << oidlist_p.size() << endl;
|
||||||
|
#endif
|
||||||
sort(oidlist_p.begin(), oidlist_p.end());
|
sort(oidlist_p.begin(), oidlist_p.end());
|
||||||
//this->kvstore->updateInsert_p2o(_pre_id, oidlist_p);
|
//this->kvstore->updateInsert_p2o(_pre_id, oidlist_p);
|
||||||
oidlist_p.clear();
|
oidlist_p.clear();
|
||||||
|
|
||||||
|
#ifdef DEBUG
|
||||||
cout << "update p2so: " << _pre_id << " " << sidoidlist_p.size() << endl;
|
cout << "update p2so: " << _pre_id << " " << sidoidlist_p.size() << endl;
|
||||||
|
#endif
|
||||||
this->kvstore->updateInsert_p2values(_pre_id, sidoidlist_p);
|
this->kvstore->updateInsert_p2values(_pre_id, sidoidlist_p);
|
||||||
sidoidlist_p.clear();
|
sidoidlist_p.clear();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
cerr << "INSERT PROCESS: OUT p2so..." << endl;
|
#ifdef DEBUG
|
||||||
|
cout << "INSERT PROCESS: OUT p2so..." << endl;
|
||||||
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -2230,7 +2287,11 @@ Database::insert(const TripleWithObjType* _triples, int _triple_num)
|
||||||
//Callers should save the vstree(node and info) after calling this function
|
//Callers should save the vstree(node and info) after calling this function
|
||||||
for (int i = 0; i < _triple_num; ++i)
|
for (int i = 0; i < _triple_num; ++i)
|
||||||
{
|
{
|
||||||
this->insertTriple(_triples[i], &vertices, &predicates);
|
bool ret = this->insertTriple(_triples[i], &vertices, &predicates);
|
||||||
|
if(ret)
|
||||||
|
{
|
||||||
|
valid_num++;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
@ -2238,19 +2299,19 @@ Database::insert(const TripleWithObjType* _triples, int _triple_num)
|
||||||
this->stringindex->change(vertices, *this->kvstore, true);
|
this->stringindex->change(vertices, *this->kvstore, true);
|
||||||
this->stringindex->change(predicates, *this->kvstore, false);
|
this->stringindex->change(predicates, *this->kvstore, false);
|
||||||
|
|
||||||
return true;
|
return valid_num;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool
|
int
|
||||||
Database::remove(const TripleWithObjType* _triples, int _triple_num)
|
Database::remove(const TripleWithObjType* _triples, int _triple_num)
|
||||||
{
|
{
|
||||||
vector<int> vertices, predicates;
|
vector<int> vertices, predicates;
|
||||||
|
int valid_num = 0;
|
||||||
|
|
||||||
#ifdef USE_GROUP_DELETE
|
#ifdef USE_GROUP_DELETE
|
||||||
//NOTICE:this is called by remove(file) or query()(but can not be too large),
|
//NOTICE:this is called by remove(file) or query()(but can not be too large),
|
||||||
//assume that db is loaded already
|
//assume that db is loaded already
|
||||||
int** id_tuples = new int*[_triple_num];
|
int** id_tuples = new int*[_triple_num];
|
||||||
int valid_num = 0;
|
|
||||||
int i = 0;
|
int i = 0;
|
||||||
//for(i = 0; i < _triple_num; ++i)
|
//for(i = 0; i < _triple_num; ++i)
|
||||||
//{
|
//{
|
||||||
|
@ -2311,7 +2372,9 @@ Database::remove(const TripleWithObjType* _triples, int _triple_num)
|
||||||
//
|
//
|
||||||
//spo cmp: s2p s2o s2po sp2o
|
//spo cmp: s2p s2o s2po sp2o
|
||||||
{
|
{
|
||||||
|
#ifdef DEBUG
|
||||||
cout << "INSRET PROCESS: to spo cmp and update" << endl;
|
cout << "INSRET PROCESS: to spo cmp and update" << endl;
|
||||||
|
#endif
|
||||||
qsort(id_tuples, valid_num, sizeof(int*), KVstore::_spo_cmp);
|
qsort(id_tuples, valid_num, sizeof(int*), KVstore::_spo_cmp);
|
||||||
vector<int> oidlist_s;
|
vector<int> oidlist_s;
|
||||||
vector<int> pidlist_s;
|
vector<int> pidlist_s;
|
||||||
|
@ -2381,11 +2444,15 @@ Database::remove(const TripleWithObjType* _triples, int _triple_num)
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
cerr << "INSERT PROCESS: OUT s2po..." << endl;
|
#ifdef DEBUG
|
||||||
|
cout << "INSERT PROCESS: OUT s2po..." << endl;
|
||||||
|
#endif
|
||||||
}
|
}
|
||||||
//ops cmp: o2p o2s o2ps op2s
|
//ops cmp: o2p o2s o2ps op2s
|
||||||
{
|
{
|
||||||
|
#ifdef DEBUG
|
||||||
cout << "INSRET PROCESS: to ops cmp and update" << endl;
|
cout << "INSRET PROCESS: to ops cmp and update" << endl;
|
||||||
|
#endif
|
||||||
qsort(id_tuples, valid_num, sizeof(int**), KVstore::_ops_cmp);
|
qsort(id_tuples, valid_num, sizeof(int**), KVstore::_ops_cmp);
|
||||||
vector<int> sidlist_o;
|
vector<int> sidlist_o;
|
||||||
vector<int> sidlist_op;
|
vector<int> sidlist_op;
|
||||||
|
@ -2476,11 +2543,15 @@ Database::remove(const TripleWithObjType* _triples, int _triple_num)
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
cerr << "INSERT PROCESS: OUT o2ps..." << endl;
|
#ifdef DEBUG
|
||||||
|
cout << "INSERT PROCESS: OUT o2ps..." << endl;
|
||||||
|
#endif
|
||||||
}
|
}
|
||||||
//pso cmp: p2s p2o p2so
|
//pso cmp: p2s p2o p2so
|
||||||
{
|
{
|
||||||
|
#ifdef DEBUG
|
||||||
cout << "INSRET PROCESS: to pso cmp and update" << endl;
|
cout << "INSRET PROCESS: to pso cmp and update" << endl;
|
||||||
|
#endif
|
||||||
qsort(id_tuples, valid_num, sizeof(int*), KVstore::_pso_cmp);
|
qsort(id_tuples, valid_num, sizeof(int*), KVstore::_pso_cmp);
|
||||||
vector<int> sidlist_p;
|
vector<int> sidlist_p;
|
||||||
vector<int> oidlist_p;
|
vector<int> oidlist_p;
|
||||||
|
@ -2530,7 +2601,9 @@ Database::remove(const TripleWithObjType* _triples, int _triple_num)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
cerr << "INSERT PROCESS: OUT p2so..." << endl;
|
#ifdef DEBUG
|
||||||
|
cout << "INSERT PROCESS: OUT p2so..." << endl;
|
||||||
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -2544,7 +2617,11 @@ Database::remove(const TripleWithObjType* _triples, int _triple_num)
|
||||||
//Callers should save the vstree(node and info) after calling this function
|
//Callers should save the vstree(node and info) after calling this function
|
||||||
for (int i = 0; i < _triple_num; ++i)
|
for (int i = 0; i < _triple_num; ++i)
|
||||||
{
|
{
|
||||||
this->removeTriple(_triples[i], &vertices, &predicates);
|
bool ret = this->removeTriple(_triples[i], &vertices, &predicates);
|
||||||
|
if(ret)
|
||||||
|
{
|
||||||
|
valid_num++;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
@ -2552,7 +2629,7 @@ Database::remove(const TripleWithObjType* _triples, int _triple_num)
|
||||||
this->stringindex->disable(vertices, true);
|
this->stringindex->disable(vertices, true);
|
||||||
this->stringindex->disable(predicates, false);
|
this->stringindex->disable(predicates, false);
|
||||||
|
|
||||||
return true;
|
return valid_num;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool
|
bool
|
||||||
|
|
|
@ -47,7 +47,7 @@ public:
|
||||||
|
|
||||||
bool load();
|
bool load();
|
||||||
bool unload();
|
bool unload();
|
||||||
bool query(const string _query, ResultSet& _result_set, FILE* _fp = stdout);
|
int query(const string _query, ResultSet& _result_set, FILE* _fp = stdout);
|
||||||
|
|
||||||
//1. if subject of _triple doesn't exist,
|
//1. if subject of _triple doesn't exist,
|
||||||
//then assign a new subid, and insert a new SigEntry
|
//then assign a new subid, and insert a new SigEntry
|
||||||
|
@ -96,6 +96,7 @@ private:
|
||||||
|
|
||||||
//pre2num mapping
|
//pre2num mapping
|
||||||
TNUM* pre2num;
|
TNUM* pre2num;
|
||||||
|
//valid: check from minNumPID to maxNumPID
|
||||||
int maxNumPID, minNumPID;
|
int maxNumPID, minNumPID;
|
||||||
void setPreMap();
|
void setPreMap();
|
||||||
//string buffer
|
//string buffer
|
||||||
|
@ -172,12 +173,12 @@ private:
|
||||||
|
|
||||||
//insert and delete, notice that modify is not needed here
|
//insert and delete, notice that modify is not needed here
|
||||||
//we can read from file or use sparql syntax
|
//we can read from file or use sparql syntax
|
||||||
int insertTriple(const TripleWithObjType& _triple, vector<int>* _vertices = NULL, vector<int>* _predicates = NULL);
|
bool insertTriple(const TripleWithObjType& _triple, vector<int>* _vertices = NULL, vector<int>* _predicates = NULL);
|
||||||
bool removeTriple(const TripleWithObjType& _triple, vector<int>* _vertices = NULL, vector<int>* _predicates = NULL);
|
bool removeTriple(const TripleWithObjType& _triple, vector<int>* _vertices = NULL, vector<int>* _predicates = NULL);
|
||||||
//NOTICE:one by one is too costly, sort and insert/delete at a time will be better
|
//NOTICE:one by one is too costly, sort and insert/delete at a time will be better
|
||||||
bool insert(const TripleWithObjType* _triples, int _triple_num);
|
int insert(const TripleWithObjType* _triples, int _triple_num);
|
||||||
//bool insert(const vector<TripleWithObjType>& _triples, vector<int>& _vertices, vector<int>& _predicates);
|
//bool insert(const vector<TripleWithObjType>& _triples, vector<int>& _vertices, vector<int>& _predicates);
|
||||||
bool remove(const TripleWithObjType* _triples, int _triple_num);
|
int remove(const TripleWithObjType* _triples, int _triple_num);
|
||||||
//bool remove(const vector<TripleWithObjType>& _triples, vector<int>& _vertices, vector<int>& _predicates);
|
//bool remove(const vector<TripleWithObjType>& _triples, vector<int>& _vertices, vector<int>& _predicates);
|
||||||
|
|
||||||
bool sub2id_pre2id_obj2id_RDFintoSignature(const string _rdf_file, int**& _p_id_tuples, int & _id_tuples_max);
|
bool sub2id_pre2id_obj2id_RDFintoSignature(const string _rdf_file, int**& _p_id_tuples, int & _id_tuples_max);
|
||||||
|
|
File diff suppressed because it is too large
Load Diff
|
@ -48,6 +48,8 @@ private:
|
||||||
BasicQuery* basic_query;
|
BasicQuery* basic_query;
|
||||||
KVstore* kvstore;
|
KVstore* kvstore;
|
||||||
TNUM* pre2num;
|
TNUM* pre2num;
|
||||||
|
int limitID_predicate;
|
||||||
|
int limitID_literal;
|
||||||
//used by score_node for parameters
|
//used by score_node for parameters
|
||||||
static const unsigned PARAM_DEGREE = 1;
|
static const unsigned PARAM_DEGREE = 1;
|
||||||
static const unsigned PARAM_SIZE = 1000000;
|
static const unsigned PARAM_SIZE = 1000000;
|
||||||
|
@ -118,7 +120,8 @@ private:
|
||||||
|
|
||||||
//BETTER?:change these params to members in class
|
//BETTER?:change these params to members in class
|
||||||
void acquire_all_id_lists(IdLists& _id_lists, IdListsLen& _id_lists_len, IDList& _can_list, vector<int>& _edges, int _id, int _can_list_size);
|
void acquire_all_id_lists(IdLists& _id_lists, IdListsLen& _id_lists_len, IDList& _can_list, vector<int>& _edges, int _id, int _can_list_size);
|
||||||
bool join_two(vector<int>& _edges, IDList& _can_list, int _can_list_size, int _id, bool _is_literal);
|
void update_answer_list(IDList*& valid_ans_list, IDList& _can_list, int* id_list, int id_list_len, bool _is_literal);
|
||||||
|
bool join_two(vector< vector<int> >& _edges, IDList& _can_list, int _can_list_size, int _id, bool _is_literal);
|
||||||
|
|
||||||
bool multi_join();
|
bool multi_join();
|
||||||
//NOTICE:this is only used to join a BasicQuery
|
//NOTICE:this is only used to join a BasicQuery
|
||||||
|
@ -126,7 +129,7 @@ private:
|
||||||
|
|
||||||
public:
|
public:
|
||||||
Join();
|
Join();
|
||||||
Join(KVstore* _kvstore, TNUM* _pre2num);
|
Join(KVstore* _kvstore, TNUM* _pre2num, int _limitID_predicate, int _limitID_literal);
|
||||||
//these functions can be called by Database
|
//these functions can be called by Database
|
||||||
bool join_sparql(SPARQLquery& _sparql_query);
|
bool join_sparql(SPARQLquery& _sparql_query);
|
||||||
bool join_basic(BasicQuery* _basic_query);
|
bool join_basic(BasicQuery* _basic_query);
|
||||||
|
|
|
@ -18,12 +18,14 @@ Strategy::Strategy()
|
||||||
//this->prepare_handler();
|
//this->prepare_handler();
|
||||||
}
|
}
|
||||||
|
|
||||||
Strategy::Strategy(KVstore* _kvstore, VSTree* _vstree, TNUM* _pre2num)
|
Strategy::Strategy(KVstore* _kvstore, VSTree* _vstree, TNUM* _pre2num, int _limitID_predicate, int _limitID_literal)
|
||||||
{
|
{
|
||||||
this->method = 0;
|
this->method = 0;
|
||||||
this->kvstore = _kvstore;
|
this->kvstore = _kvstore;
|
||||||
this->vstree = _vstree;
|
this->vstree = _vstree;
|
||||||
this->pre2num = _pre2num;
|
this->pre2num = _pre2num;
|
||||||
|
this->limitID_predicate = _limitID_predicate;
|
||||||
|
this->limitID_literal = _limitID_literal;
|
||||||
//this->prepare_handler();
|
//this->prepare_handler();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -40,7 +42,7 @@ Strategy::~Strategy()
|
||||||
//}
|
//}
|
||||||
|
|
||||||
//NOTICE: 2-triple case ?s1 p1 c0 ?s2 p2 c0 is viewed as an unconnected graph
|
//NOTICE: 2-triple case ?s1 p1 c0 ?s2 p2 c0 is viewed as an unconnected graph
|
||||||
//however, this can be dealed due to several basicquery and linking
|
//however, this can be dealed due to several basic queries and linking
|
||||||
|
|
||||||
bool
|
bool
|
||||||
Strategy::handle(SPARQLquery& _query, ResultFilter* _result_filter)
|
Strategy::handle(SPARQLquery& _query, ResultFilter* _result_filter)
|
||||||
|
@ -54,84 +56,24 @@ Strategy::handle(SPARQLquery& _query, ResultFilter* _result_filter)
|
||||||
for (; iter != queryList.end(); iter++)
|
for (; iter != queryList.end(); iter++)
|
||||||
if ((**iter).getEncodeBasicQueryResult())
|
if ((**iter).getEncodeBasicQueryResult())
|
||||||
{
|
{
|
||||||
this->method = 0;
|
this->method = -1;
|
||||||
|
|
||||||
vector<int*>& result_list = (*iter)->getResultList();
|
vector<int*>& result_list = (*iter)->getResultList();
|
||||||
//int select_var_num = (*iter)->getSelectVarNum();
|
//int select_var_num = (*iter)->getSelectVarNum();
|
||||||
int varNum = (*iter)->getVarNum(); //the num of vars needing to be joined
|
//the num of vars needing to be joined, i.e. selectVarNum if only one triple
|
||||||
|
int varNum = (*iter)->getVarNum();
|
||||||
|
//all variables(not including pre vars)
|
||||||
int total_num = (*iter)->getTotalVarNum();
|
int total_num = (*iter)->getTotalVarNum();
|
||||||
int pre_varNum = (*iter)->getPreVarNum();
|
int pre_varNum = (*iter)->getPreVarNum();
|
||||||
|
int selected_pre_var_num = (*iter)->getSelectedPreVarNum();
|
||||||
|
int selected_var_num = (*iter)->getSelectVarNum();
|
||||||
|
|
||||||
//TODO:if need to return pre var?
|
|
||||||
if ((*iter)->getTripleNum() == 1 && pre_varNum == 1)
|
if ((*iter)->getTripleNum() == 1 && pre_varNum == 1)
|
||||||
{
|
{
|
||||||
Triple triple = (*iter)->getTriple(0);
|
this->method = 4;
|
||||||
int* id_list = NULL;
|
|
||||||
int id_list_len = 0;
|
|
||||||
result_list.clear();
|
|
||||||
|
|
||||||
if (total_num == 2)
|
|
||||||
{
|
|
||||||
//TODO:consider special case, select ?s (?p) ?o where { ?s ?p ?o . }
|
|
||||||
//filter and join is too costly, should enum all predicates and use p2so
|
|
||||||
//maybe the selected vars are ?s (?p) or ?o (?p)
|
|
||||||
cerr << "not supported now!" << endl;
|
|
||||||
}
|
|
||||||
else if (total_num == 1)
|
|
||||||
{
|
|
||||||
//TODO:if just select s/o, use o2s/s2o
|
|
||||||
//if only p is selected, use s2p or o2p
|
|
||||||
//only if both s/o and p are selected, use s2po or o2ps
|
|
||||||
|
|
||||||
if(triple.subject[0] != '?') //constant
|
|
||||||
{
|
|
||||||
int sid = (this->kvstore)->getIDByEntity(triple.subject);
|
|
||||||
this->kvstore->getpreIDobjIDlistBysubID(sid, id_list, id_list_len);
|
|
||||||
}
|
|
||||||
else if(triple.object[0] != '?') //constant
|
|
||||||
{
|
|
||||||
int oid = (this->kvstore)->getIDByEntity(triple.object);
|
|
||||||
if (oid == -1)
|
|
||||||
{
|
|
||||||
oid = (this->kvstore)->getIDByLiteral(triple.object);
|
|
||||||
}
|
|
||||||
this->kvstore->getpreIDsubIDlistByobjID(oid, id_list, id_list_len);
|
|
||||||
}
|
|
||||||
|
|
||||||
//always place s/o before p in result list
|
|
||||||
for (int i = 0; i < id_list_len; i += 2)
|
|
||||||
{
|
|
||||||
int* record = new int[2]; //2 vars selected
|
|
||||||
record[1] = id_list[i]; //for the pre var
|
|
||||||
record[0] = id_list[i + 1]; //for the s/o var
|
|
||||||
result_list.push_back(record);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else if (total_num == 0) //only ?p
|
|
||||||
{
|
|
||||||
//just use so2p
|
|
||||||
int sid = (this->kvstore)->getIDByEntity(triple.subject);
|
|
||||||
int oid = (this->kvstore)->getIDByEntity(triple.object);
|
|
||||||
if (oid == -1)
|
|
||||||
{
|
|
||||||
oid = (this->kvstore)->getIDByLiteral(triple.object);
|
|
||||||
}
|
|
||||||
|
|
||||||
this->kvstore->getpreIDlistBysubIDobjID(sid, oid, id_list, id_list_len);
|
|
||||||
//copy to result list
|
|
||||||
for (int i = 0; i < id_list_len; ++i)
|
|
||||||
{
|
|
||||||
int* record = new int[1];
|
|
||||||
record[0] = id_list[i];
|
|
||||||
result_list.push_back(record);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
delete[] id_list;
|
|
||||||
continue;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if (pre_varNum == 0 && (*iter)->getTripleNum() == 1) //only one triple and no predicates
|
if (this->method < 0 && pre_varNum == 0 && (*iter)->getTripleNum() == 1) //only one triple and no predicates
|
||||||
{
|
{
|
||||||
//only one variable and one triple: ?s pre obj or sub pre ?o
|
//only one variable and one triple: ?s pre obj or sub pre ?o
|
||||||
if (total_num == 1)
|
if (total_num == 1)
|
||||||
|
@ -150,16 +92,22 @@ Strategy::handle(SPARQLquery& _query, ResultFilter* _result_filter)
|
||||||
this->method = 3;
|
this->method = 3;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
//cerr << "this BasicQuery use query strategy 2" << endl;
|
//cout << "this BasicQuery use query strategy 2" << endl;
|
||||||
//cerr<<"Final result size: "<<(*iter)->getResultList().size()<<endl;
|
//cout<<"Final result size: "<<(*iter)->getResultList().size()<<endl;
|
||||||
//continue;
|
//continue;
|
||||||
}
|
}
|
||||||
|
if(this->method< 0)
|
||||||
|
{
|
||||||
|
this->method = 0;
|
||||||
|
}
|
||||||
|
|
||||||
//QueryHandler dispatch;
|
//QueryHandler dispatch;
|
||||||
//dispatch[0] = handler0;
|
//dispatch[0] = handler0;
|
||||||
switch (this->method)
|
switch (this->method)
|
||||||
{
|
{
|
||||||
|
//BETTER: use function pointer array in C++ class
|
||||||
case 0:
|
case 0:
|
||||||
|
//default:filter by vstree and then verified by join
|
||||||
this->handler0(*iter, result_list, _result_filter);
|
this->handler0(*iter, result_list, _result_filter);
|
||||||
break;
|
break;
|
||||||
case 1:
|
case 1:
|
||||||
|
@ -171,21 +119,23 @@ Strategy::handle(SPARQLquery& _query, ResultFilter* _result_filter)
|
||||||
case 3:
|
case 3:
|
||||||
this->handler3(*iter, result_list);
|
this->handler3(*iter, result_list);
|
||||||
break;
|
break;
|
||||||
|
case 4:
|
||||||
|
this->handler4(*iter, result_list);
|
||||||
|
break;
|
||||||
default:
|
default:
|
||||||
cerr << "not support this method" << endl;
|
cout << "not support this method" << endl;
|
||||||
|
|
||||||
}
|
}
|
||||||
cerr << "Final result size: " << (*iter)->getResultList().size() << endl;
|
cout << "BasicQuery -- Final result size: " << (*iter)->getResultList().size() << endl;
|
||||||
//BETTER: use function pointer array in C++ class
|
|
||||||
}
|
}
|
||||||
#else
|
#else
|
||||||
cerr << "this BasicQuery use original query strategy" << endl;
|
cout << "this BasicQuery use original query strategy" << endl;
|
||||||
long tv_handle = Util::get_cur_time();
|
long tv_handle = Util::get_cur_time();
|
||||||
(this->vstree)->retrieve(_query);
|
(this->vstree)->retrieve(_query);
|
||||||
long tv_retrieve = Util::get_cur_time();
|
long tv_retrieve = Util::get_cur_time();
|
||||||
cout << "after Retrieve, used " << (tv_retrieve - tv_handle) << "ms." << endl;
|
cout << "after Retrieve, used " << (tv_retrieve - tv_handle) << "ms." << endl;
|
||||||
|
|
||||||
this->join = new Join(kvstore, pre2num);
|
this->join = new Join(kvstore, pre2num, this->limitID_predicate, this->limitID_literal);
|
||||||
this->join->join_sparql(_query);
|
this->join->join_sparql(_query);
|
||||||
delete this->join;
|
delete this->join;
|
||||||
|
|
||||||
|
@ -200,7 +150,7 @@ void
|
||||||
Strategy::handler0(BasicQuery* _bq, vector<int*>& _result_list, ResultFilter* _result_filter)
|
Strategy::handler0(BasicQuery* _bq, vector<int*>& _result_list, ResultFilter* _result_filter)
|
||||||
{
|
{
|
||||||
//long before_filter = Util::get_cur_time();
|
//long before_filter = Util::get_cur_time();
|
||||||
cerr << "this BasicQuery use query strategy 0" << endl;
|
cout << "this BasicQuery use query strategy 0" << endl;
|
||||||
|
|
||||||
//BETTER:not all vars in join filtered by vstree
|
//BETTER:not all vars in join filtered by vstree
|
||||||
//(A)-B-c: B should by vstree, then by c, but A should be generated in join(first set A as not)
|
//(A)-B-c: B should by vstree, then by c, but A should be generated in join(first set A as not)
|
||||||
|
@ -226,6 +176,7 @@ Strategy::handler0(BasicQuery* _bq, vector<int*>& _result_list, ResultFilter* _r
|
||||||
this->vstree->retrieveEntity(entityBitSet, idListPtr);
|
this->vstree->retrieveEntity(entityBitSet, idListPtr);
|
||||||
if (!flag)
|
if (!flag)
|
||||||
{
|
{
|
||||||
|
//cout<<"set ready: "<<i<<endl;
|
||||||
_bq->setReady(i);
|
_bq->setReady(i);
|
||||||
}
|
}
|
||||||
//the basic query should end if one non-literal var has no candidates
|
//the basic query should end if one non-literal var has no candidates
|
||||||
|
@ -235,8 +186,6 @@ Strategy::handler0(BasicQuery* _bq, vector<int*>& _result_list, ResultFilter* _r
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
//if(_bq->isReady(0))
|
|
||||||
//cout<<"error: var 0 is ready?"<<endl;
|
|
||||||
//TODO:end directly if one is empty!
|
//TODO:end directly if one is empty!
|
||||||
|
|
||||||
long tv_retrieve = Util::get_cur_time();
|
long tv_retrieve = Util::get_cur_time();
|
||||||
|
@ -246,7 +195,7 @@ Strategy::handler0(BasicQuery* _bq, vector<int*>& _result_list, ResultFilter* _r
|
||||||
if (_result_filter != NULL)
|
if (_result_filter != NULL)
|
||||||
_result_filter->candFilterWithResultHashTable(*_bq);
|
_result_filter->candFilterWithResultHashTable(*_bq);
|
||||||
|
|
||||||
Join *join = new Join(kvstore, pre2num);
|
Join *join = new Join(kvstore, pre2num, this->limitID_predicate, this->limitID_literal);
|
||||||
join->join_basic(_bq);
|
join->join_basic(_bq);
|
||||||
delete join;
|
delete join;
|
||||||
|
|
||||||
|
@ -258,7 +207,7 @@ void
|
||||||
Strategy::handler1(BasicQuery* _bq, vector<int*>& _result_list)
|
Strategy::handler1(BasicQuery* _bq, vector<int*>& _result_list)
|
||||||
{
|
{
|
||||||
long before_filter = Util::get_cur_time();
|
long before_filter = Util::get_cur_time();
|
||||||
cerr << "this BasicQuery use query strategy 1" << endl;
|
cout << "this BasicQuery use query strategy 1" << endl;
|
||||||
//int neighbor_id = (*_bq->getEdgeNeighborID(0, 0); //constant, -1
|
//int neighbor_id = (*_bq->getEdgeNeighborID(0, 0); //constant, -1
|
||||||
char edge_type = _bq->getEdgeType(0, 0);
|
char edge_type = _bq->getEdgeType(0, 0);
|
||||||
int triple_id = _bq->getEdgeID(0, 0);
|
int triple_id = _bq->getEdgeID(0, 0);
|
||||||
|
@ -268,7 +217,7 @@ Strategy::handler1(BasicQuery* _bq, vector<int*>& _result_list)
|
||||||
int id_list_len = 0;
|
int id_list_len = 0;
|
||||||
if (edge_type == Util::EDGE_OUT)
|
if (edge_type == Util::EDGE_OUT)
|
||||||
{
|
{
|
||||||
//cerr<<"edge out!!!"<<endl;
|
//cout<<"edge out!!!"<<endl;
|
||||||
int nid = (this->kvstore)->getIDByEntity(triple.object);
|
int nid = (this->kvstore)->getIDByEntity(triple.object);
|
||||||
if (nid == -1)
|
if (nid == -1)
|
||||||
{
|
{
|
||||||
|
@ -278,32 +227,32 @@ Strategy::handler1(BasicQuery* _bq, vector<int*>& _result_list)
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
//cerr<<"edge in!!!"<<endl;
|
//cout<<"edge in!!!"<<endl;
|
||||||
this->kvstore->getobjIDlistBysubIDpreID(this->kvstore->getIDByEntity(triple.subject), pre_id, id_list, id_list_len);
|
this->kvstore->getobjIDlistBysubIDpreID(this->kvstore->getIDByEntity(triple.subject), pre_id, id_list, id_list_len);
|
||||||
}
|
}
|
||||||
|
|
||||||
long after_filter = Util::get_cur_time();
|
long after_filter = Util::get_cur_time();
|
||||||
cerr << "after filter, used " << (after_filter - before_filter) << "ms" << endl;
|
cout << "after filter, used " << (after_filter - before_filter) << "ms" << endl;
|
||||||
_result_list.clear();
|
_result_list.clear();
|
||||||
//cerr<<"now to copy result to list"<<endl;
|
//cout<<"now to copy result to list"<<endl;
|
||||||
for (int i = 0; i < id_list_len; ++i)
|
for (int i = 0; i < id_list_len; ++i)
|
||||||
{
|
{
|
||||||
int* record = new int[1]; //only this var is selected
|
int* record = new int[1]; //only this var is selected
|
||||||
record[0] = id_list[i];
|
record[0] = id_list[i];
|
||||||
//cerr<<this->kvstore->getEntityByID(record[0])<<endl;
|
//cout<<this->kvstore->getEntityByID(record[0])<<endl;
|
||||||
_result_list.push_back(record);
|
_result_list.push_back(record);
|
||||||
}
|
}
|
||||||
long after_copy = Util::get_cur_time();
|
long after_copy = Util::get_cur_time();
|
||||||
cerr << "after copy to result list: used " << (after_copy - after_filter) << " ms" << endl;
|
cout << "after copy to result list: used " << (after_copy - after_filter) << " ms" << endl;
|
||||||
delete[] id_list;
|
delete[] id_list;
|
||||||
cerr << "Final result size: " << _result_list.size() << endl;
|
cout << "Final result size: " << _result_list.size() << endl;
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
Strategy::handler2(BasicQuery* _bq, vector<int*>& _result_list)
|
Strategy::handler2(BasicQuery* _bq, vector<int*>& _result_list)
|
||||||
{
|
{
|
||||||
long before_filter = Util::get_cur_time();
|
long before_filter = Util::get_cur_time();
|
||||||
cerr << "this BasicQuery use query strategy 2" << endl;
|
cout << "this BasicQuery use query strategy 2" << endl;
|
||||||
int triple_id = _bq->getEdgeID(0, 0);
|
int triple_id = _bq->getEdgeID(0, 0);
|
||||||
Triple triple = _bq->getTriple(triple_id);
|
Triple triple = _bq->getTriple(triple_id);
|
||||||
int pre_id = _bq->getEdgePreID(0, 0);
|
int pre_id = _bq->getEdgePreID(0, 0);
|
||||||
|
@ -326,10 +275,10 @@ Strategy::handler2(BasicQuery* _bq, vector<int*>& _result_list)
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
cerr << "ERROR in Database::handle(): no selected var!" << endl;
|
cout << "ERROR in Database::handle(): no selected var!" << endl;
|
||||||
}
|
}
|
||||||
long after_filter = Util::get_cur_time();
|
long after_filter = Util::get_cur_time();
|
||||||
cerr << "after filter, used " << (after_filter - before_filter) << "ms" << endl;
|
cout << "after filter, used " << (after_filter - before_filter) << "ms" << endl;
|
||||||
_result_list.clear();
|
_result_list.clear();
|
||||||
for (int i = 0; i < id_list_len; ++i)
|
for (int i = 0; i < id_list_len; ++i)
|
||||||
{
|
{
|
||||||
|
@ -338,16 +287,16 @@ Strategy::handler2(BasicQuery* _bq, vector<int*>& _result_list)
|
||||||
_result_list.push_back(record);
|
_result_list.push_back(record);
|
||||||
}
|
}
|
||||||
long after_copy = Util::get_cur_time();
|
long after_copy = Util::get_cur_time();
|
||||||
cerr << "after copy to result list: used " << (after_copy - after_filter) << " ms" << endl;
|
cout << "after copy to result list: used " << (after_copy - after_filter) << " ms" << endl;
|
||||||
delete[] id_list;
|
delete[] id_list;
|
||||||
cerr << "Final result size: " << _result_list.size() << endl;
|
cout << "Final result size: " << _result_list.size() << endl;
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
Strategy::handler3(BasicQuery* _bq, vector<int*>& _result_list)
|
Strategy::handler3(BasicQuery* _bq, vector<int*>& _result_list)
|
||||||
{
|
{
|
||||||
long before_filter = Util::get_cur_time();
|
long before_filter = Util::get_cur_time();
|
||||||
cerr << "this BasicQuery use query strategy 3" << endl;
|
cout << "this BasicQuery use query strategy 3" << endl;
|
||||||
int triple_id = _bq->getEdgeID(0, 0);
|
int triple_id = _bq->getEdgeID(0, 0);
|
||||||
Triple triple = _bq->getTriple(triple_id);
|
Triple triple = _bq->getTriple(triple_id);
|
||||||
int pre_id = _bq->getEdgePreID(0, 0);
|
int pre_id = _bq->getEdgePreID(0, 0);
|
||||||
|
@ -356,8 +305,8 @@ Strategy::handler3(BasicQuery* _bq, vector<int*>& _result_list)
|
||||||
|
|
||||||
_result_list.clear();
|
_result_list.clear();
|
||||||
this->kvstore->getsubIDobjIDlistBypreID(pre_id, id_list, id_list_len);
|
this->kvstore->getsubIDobjIDlistBypreID(pre_id, id_list, id_list_len);
|
||||||
int var1_id = _bq->getIDByVarName(triple.subject);
|
int var1_id = _bq->getSelectedVarPosition(triple.subject);
|
||||||
int var2_id = _bq->getIDByVarName(triple.object);
|
int var2_id = _bq->getSelectedVarPosition(triple.object);
|
||||||
|
|
||||||
if(var1_id < 0 || var2_id < 0)
|
if(var1_id < 0 || var2_id < 0)
|
||||||
{
|
{
|
||||||
|
@ -366,7 +315,7 @@ Strategy::handler3(BasicQuery* _bq, vector<int*>& _result_list)
|
||||||
}
|
}
|
||||||
|
|
||||||
long after_filter = Util::get_cur_time();
|
long after_filter = Util::get_cur_time();
|
||||||
cerr << "after filter, used " << (after_filter - before_filter) << "ms" << endl;
|
cout << "after filter, used " << (after_filter - before_filter) << "ms" << endl;
|
||||||
|
|
||||||
for (int i = 0; i < id_list_len; i += 2)
|
for (int i = 0; i < id_list_len; i += 2)
|
||||||
{
|
{
|
||||||
|
@ -377,7 +326,134 @@ Strategy::handler3(BasicQuery* _bq, vector<int*>& _result_list)
|
||||||
}
|
}
|
||||||
|
|
||||||
long after_copy = Util::get_cur_time();
|
long after_copy = Util::get_cur_time();
|
||||||
cerr << "after copy to result list: used " << (after_copy - after_filter) << " ms" << endl;
|
cout << "after copy to result list: used " << (after_copy - after_filter) << " ms" << endl;
|
||||||
delete[] id_list;
|
delete[] id_list;
|
||||||
cerr << "Final result size: " << _result_list.size() << endl;
|
cout << "Final result size: " << _result_list.size() << endl;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
Strategy::handler4(BasicQuery* _bq, vector<int*>& _result_list)
|
||||||
|
{
|
||||||
|
cout<<"Special Case: consider pre var in this triple"<<endl;
|
||||||
|
int varNum = _bq->getVarNum();
|
||||||
|
//all variables(not including pre vars)
|
||||||
|
int total_num = _bq->getTotalVarNum();
|
||||||
|
int pre_varNum = _bq->getPreVarNum();
|
||||||
|
int selected_pre_var_num = _bq->getSelectedPreVarNum();
|
||||||
|
int selected_var_num = _bq->getSelectVarNum();
|
||||||
|
Triple triple = _bq->getTriple(0);
|
||||||
|
int pvpos = _bq->getSelectedPreVarPosition(triple.predicate);
|
||||||
|
int* id_list = NULL;
|
||||||
|
int id_list_len = 0;
|
||||||
|
_result_list.clear();
|
||||||
|
|
||||||
|
//cout<<"total num: "<<total_num <<endl;
|
||||||
|
if (total_num == 2)
|
||||||
|
{
|
||||||
|
cout<<"Special Case 1"<<endl;
|
||||||
|
int svpos = _bq->getSelectedVarPosition(triple.subject);
|
||||||
|
int ovpos = _bq->getSelectedVarPosition(triple.object);
|
||||||
|
cout<<"subject: "<<triple.subject<<" "<<svpos<<endl;
|
||||||
|
cout<<"object: "<<triple.object<<" "<<ovpos<<endl;
|
||||||
|
cout<<"predicate: "<<triple.predicate<<" "<<pvpos<<endl;
|
||||||
|
//very special case, to find all triples, select ?s (?p) ?o where { ?s ?p ?o . }
|
||||||
|
//filter and join is too costly, should enum all predicates and use p2so
|
||||||
|
for(int i = 0; i < this->limitID_predicate; ++i)
|
||||||
|
{
|
||||||
|
int pid = i;
|
||||||
|
this->kvstore->getsubIDobjIDlistBypreID(pid, id_list, id_list_len);
|
||||||
|
int rsize = selected_var_num;
|
||||||
|
if(selected_pre_var_num == 1)
|
||||||
|
{
|
||||||
|
rsize++;
|
||||||
|
}
|
||||||
|
|
||||||
|
//always place s/o before p in result list
|
||||||
|
for (int j = 0; j < id_list_len; j += 2)
|
||||||
|
{
|
||||||
|
int* record = new int[rsize];
|
||||||
|
//check the s/o var if selected, need to ensure the placement order
|
||||||
|
if(ovpos >= 0)
|
||||||
|
{
|
||||||
|
record[ovpos] = id_list[j+1];
|
||||||
|
}
|
||||||
|
if(svpos >= 0)
|
||||||
|
{
|
||||||
|
record[svpos] = id_list[j];
|
||||||
|
}
|
||||||
|
|
||||||
|
if(pvpos >= 0)
|
||||||
|
{
|
||||||
|
record[pvpos] = pid; //for the pre var
|
||||||
|
}
|
||||||
|
_result_list.push_back(record);
|
||||||
|
}
|
||||||
|
delete[] id_list;
|
||||||
|
}
|
||||||
|
id_list = NULL;
|
||||||
|
}
|
||||||
|
else if (total_num == 1)
|
||||||
|
{
|
||||||
|
cout<<"Special Case 2"<<endl;
|
||||||
|
int vpos = -1;
|
||||||
|
if(triple.subject[0] != '?') //constant
|
||||||
|
{
|
||||||
|
int sid = (this->kvstore)->getIDByEntity(triple.subject);
|
||||||
|
this->kvstore->getpreIDobjIDlistBysubID(sid, id_list, id_list_len);
|
||||||
|
vpos = _bq->getSelectedVarPosition(triple.object);
|
||||||
|
}
|
||||||
|
else if(triple.object[0] != '?') //constant
|
||||||
|
{
|
||||||
|
int oid = (this->kvstore)->getIDByEntity(triple.object);
|
||||||
|
if (oid == -1)
|
||||||
|
{
|
||||||
|
oid = (this->kvstore)->getIDByLiteral(triple.object);
|
||||||
|
}
|
||||||
|
this->kvstore->getpreIDsubIDlistByobjID(oid, id_list, id_list_len);
|
||||||
|
vpos = _bq->getSelectedVarPosition(triple.subject);
|
||||||
|
}
|
||||||
|
|
||||||
|
int rsize = varNum;
|
||||||
|
if(selected_pre_var_num == 1)
|
||||||
|
{
|
||||||
|
rsize++;
|
||||||
|
}
|
||||||
|
//always place s/o before p in result list
|
||||||
|
for (int i = 0; i < id_list_len; i += 2)
|
||||||
|
{
|
||||||
|
int* record = new int[rsize];
|
||||||
|
if(vpos >= 0)
|
||||||
|
{
|
||||||
|
record[vpos] = id_list[i + 1]; //for the s/o var
|
||||||
|
}
|
||||||
|
if(pvpos >= 0)
|
||||||
|
{
|
||||||
|
record[pvpos] = id_list[i]; //for the pre var
|
||||||
|
}
|
||||||
|
_result_list.push_back(record);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else if (total_num == 0) //only ?p and it must be selected
|
||||||
|
{
|
||||||
|
cout<<"Special Case 3"<<endl;
|
||||||
|
//just use so2p
|
||||||
|
int sid = (this->kvstore)->getIDByEntity(triple.subject);
|
||||||
|
int oid = (this->kvstore)->getIDByEntity(triple.object);
|
||||||
|
if (oid == -1)
|
||||||
|
{
|
||||||
|
oid = (this->kvstore)->getIDByLiteral(triple.object);
|
||||||
|
}
|
||||||
|
|
||||||
|
this->kvstore->getpreIDlistBysubIDobjID(sid, oid, id_list, id_list_len);
|
||||||
|
//copy to result list
|
||||||
|
for (int i = 0; i < id_list_len; ++i)
|
||||||
|
{
|
||||||
|
int* record = new int[1];
|
||||||
|
record[0] = id_list[i];
|
||||||
|
_result_list.push_back(record);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
delete[] id_list;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
|
@ -23,7 +23,7 @@ class Strategy
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
Strategy();
|
Strategy();
|
||||||
Strategy(KVstore*, VSTree*, TNUM*);
|
Strategy(KVstore*, VSTree*, TNUM*, int, int);
|
||||||
~Strategy();
|
~Strategy();
|
||||||
//select efficient strategy to do the sparql query
|
//select efficient strategy to do the sparql query
|
||||||
bool handle(SPARQLquery&, ResultFilter* _result_filter = NULL);
|
bool handle(SPARQLquery&, ResultFilter* _result_filter = NULL);
|
||||||
|
@ -33,10 +33,14 @@ private:
|
||||||
KVstore* kvstore;
|
KVstore* kvstore;
|
||||||
VSTree* vstree;
|
VSTree* vstree;
|
||||||
TNUM* pre2num;
|
TNUM* pre2num;
|
||||||
|
int limitID_predicate;
|
||||||
|
int limitID_literal;
|
||||||
|
|
||||||
void handler0(BasicQuery*, vector<int*>&, ResultFilter* _result_filter = NULL);
|
void handler0(BasicQuery*, vector<int*>&, ResultFilter* _result_filter = NULL);
|
||||||
void handler1(BasicQuery*, vector<int*>&);
|
void handler1(BasicQuery*, vector<int*>&);
|
||||||
void handler2(BasicQuery*, vector<int*>&);
|
void handler2(BasicQuery*, vector<int*>&);
|
||||||
void handler3(BasicQuery*, vector<int*>&);
|
void handler3(BasicQuery*, vector<int*>&);
|
||||||
|
void handler4(BasicQuery*, vector<int*>&);
|
||||||
//QueryHandler *dispatch;
|
//QueryHandler *dispatch;
|
||||||
//void prepare_handler();
|
//void prepare_handler();
|
||||||
};
|
};
|
||||||
|
|
|
@ -1108,6 +1108,7 @@ string KVstore::getLiteralByID(int _id) const {
|
||||||
int _len = 0;
|
int _len = 0;
|
||||||
bool _get = this->getValueByKey(this->id2literal, _id, _tmp, _len);
|
bool _get = this->getValueByKey(this->id2literal, _id, _tmp, _len);
|
||||||
if (!_get) {
|
if (!_get) {
|
||||||
|
//NOTICE:here assumes that all literals cannot be empty: ""
|
||||||
return "";
|
return "";
|
||||||
}
|
}
|
||||||
string _ret = string(_tmp);
|
string _ret = string(_tmp);
|
||||||
|
@ -1971,4 +1972,4 @@ unsigned short KVstore::buffer_oID2values_build = 32;
|
||||||
unsigned short KVstore::buffer_pID2values_build = 16;
|
unsigned short KVstore::buffer_pID2values_build = 16;
|
||||||
unsigned short KVstore::buffer_sID2values_query = 16;
|
unsigned short KVstore::buffer_sID2values_query = 16;
|
||||||
unsigned short KVstore::buffer_oID2values_query = 16;
|
unsigned short KVstore::buffer_oID2values_query = 16;
|
||||||
unsigned short KVstore::buffer_pID2values_query = 8;
|
unsigned short KVstore::buffer_pID2values_query = 8;
|
||||||
|
|
|
@ -20,6 +20,13 @@ main(int argc, char * argv[])
|
||||||
#ifdef DEBUG
|
#ifdef DEBUG
|
||||||
Util util;
|
Util util;
|
||||||
#endif
|
#endif
|
||||||
|
if(argc == 1) //./gbuild
|
||||||
|
{
|
||||||
|
//output help info here
|
||||||
|
cout << "the usage of gbuild: " << endl;
|
||||||
|
cout << "bin/gbuild your_database_name.db your_dataset_path" << endl;
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
//system("clock");
|
//system("clock");
|
||||||
cout << "gbuild..." << endl;
|
cout << "gbuild..." << endl;
|
||||||
{
|
{
|
||||||
|
|
|
@ -114,7 +114,6 @@ FILE* output = stdout;
|
||||||
//current using database in local
|
//current using database in local
|
||||||
Database *current_database = NULL;
|
Database *current_database = NULL;
|
||||||
|
|
||||||
//TODO:redirect 2>&1 or adjust the fprintf->stderr to file pointer
|
|
||||||
int
|
int
|
||||||
main(int argc, char **argv)
|
main(int argc, char **argv)
|
||||||
{
|
{
|
||||||
|
@ -128,34 +127,35 @@ main(int argc, char **argv)
|
||||||
char *line, *s;
|
char *line, *s;
|
||||||
progname = argv[0];
|
progname = argv[0];
|
||||||
|
|
||||||
long cur_path_len;
|
//NOTICE+DEBUG: the code segment below is used to change directory if not in gStore root, but here exists some bugs
|
||||||
char* cur_work_dir;
|
//long cur_path_len;
|
||||||
if ((cur_path_len = pathconf(".", _PC_PATH_MAX)) == -1) {
|
//char* cur_work_dir;
|
||||||
cerr << "Couldn't get current working path length" << endl;
|
//if ((cur_path_len = pathconf(".", _PC_PATH_MAX)) == -1) {
|
||||||
return 1;
|
//cerr << "Couldn't get current working path length" << endl;
|
||||||
}
|
//return 1;
|
||||||
if ((cur_work_dir = (char*)malloc(cur_path_len + 1 + strlen(progname))) == NULL) {
|
//}
|
||||||
cerr << "Couldn't allocate memory for the pathname" << endl;
|
//if ((cur_work_dir = (char*)malloc(cur_path_len + 1 + strlen(progname))) == NULL) {
|
||||||
return 1;
|
//cerr << "Couldn't allocate memory for the pathname" << endl;
|
||||||
}
|
//return 1;
|
||||||
if (getcwd(cur_work_dir, cur_path_len) == NULL) {
|
//}
|
||||||
cerr << "Couldn't get current working directory!" << endl;
|
//if (getcwd(cur_work_dir, cur_path_len) == NULL) {
|
||||||
return 1;
|
//cerr << "Couldn't get current working directory!" << endl;
|
||||||
}
|
//return 1;
|
||||||
strcat(cur_work_dir, "/");
|
//}
|
||||||
strcat(cur_work_dir, progname);
|
//strcat(cur_work_dir, "/");
|
||||||
char* dir_name = dirname(cur_work_dir);
|
//strcat(cur_work_dir, progname);
|
||||||
free(cur_work_dir);
|
//char* dir_name = dirname(cur_work_dir);
|
||||||
if (dir_name == NULL) {
|
//free(cur_work_dir);
|
||||||
cerr << "Couldn't get current directory name!" << endl;
|
//if (dir_name == NULL) {
|
||||||
return 1;
|
//cerr << "Couldn't get current directory name!" << endl;
|
||||||
}
|
//return 1;
|
||||||
string root(dir_name);
|
//}
|
||||||
root += "/..";
|
//string root(dir_name);
|
||||||
if (chdir(root.c_str()) == -1) {
|
//root += "/..";
|
||||||
cerr << "Couldn't change current directory!" << endl;
|
//if (chdir(root.c_str()) == -1) {
|
||||||
return 1;
|
//cerr << "Couldn't change current directory!" << endl;
|
||||||
}
|
//return 1;
|
||||||
|
//}
|
||||||
|
|
||||||
system("clear");
|
system("clear");
|
||||||
|
|
||||||
|
@ -1171,4 +1171,31 @@ int printport_handler(const vector<string>& args) {
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
return system("bin/gserver -P");
|
return system("bin/gserver -P");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -50,7 +50,7 @@ main(int argc, char * argv[])
|
||||||
cout << "gquery..." << endl;
|
cout << "gquery..." << endl;
|
||||||
if (argc < 2)
|
if (argc < 2)
|
||||||
{
|
{
|
||||||
cerr << "error: lack of DB_store to be queried" << endl;
|
cout << "error: lack of DB_store to be queried" << endl;
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
{
|
{
|
||||||
|
@ -100,11 +100,48 @@ main(int argc, char * argv[])
|
||||||
}
|
}
|
||||||
printf("query is:\n%s\n\n", query.c_str());
|
printf("query is:\n%s\n\n", query.c_str());
|
||||||
ResultSet _rs;
|
ResultSet _rs;
|
||||||
_db.query(query, _rs, stdout);
|
FILE* ofp = stdout;
|
||||||
if (argc >= 4)
|
if (argc >= 4)
|
||||||
{
|
{
|
||||||
Util::save_to_file(argv[3], _rs.to_str());
|
ofp = fopen(argv[3], "w");
|
||||||
}
|
}
|
||||||
|
string msg;
|
||||||
|
int ret = _db.query(query, _rs, ofp);
|
||||||
|
|
||||||
|
if(argc >= 4)
|
||||||
|
{
|
||||||
|
fclose(ofp);
|
||||||
|
ofp = NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
//cout<<"gquery ret: "<<ret<<endl;
|
||||||
|
if (ret <= -100) //select query
|
||||||
|
{
|
||||||
|
if(ret == -100)
|
||||||
|
{
|
||||||
|
msg = _rs.to_str();
|
||||||
|
}
|
||||||
|
else //query error
|
||||||
|
{
|
||||||
|
msg = "query failed.";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else //update query
|
||||||
|
{
|
||||||
|
if(ret >= 0)
|
||||||
|
{
|
||||||
|
msg = "update num: " + Util::int2string(ret);
|
||||||
|
}
|
||||||
|
else //update error
|
||||||
|
{
|
||||||
|
msg = "update failed.";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if(ret != -100)
|
||||||
|
{
|
||||||
|
cout << msg <<endl;
|
||||||
|
}
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -220,7 +257,39 @@ main(int argc, char * argv[])
|
||||||
printf("query is:\n");
|
printf("query is:\n");
|
||||||
printf("%s\n\n", query.c_str());
|
printf("%s\n\n", query.c_str());
|
||||||
ResultSet _rs;
|
ResultSet _rs;
|
||||||
_db.query(query, _rs, fp);
|
int ret = _db.query(query, _rs, fp);
|
||||||
|
//int ret = _db.query(query, _rs, NULL);
|
||||||
|
string msg;
|
||||||
|
|
||||||
|
//cout<<"gquery ret: "<<ret<<endl;
|
||||||
|
if (ret <= -100) //select query
|
||||||
|
{
|
||||||
|
if(ret == -100)
|
||||||
|
{
|
||||||
|
msg = "";
|
||||||
|
}
|
||||||
|
else //query error
|
||||||
|
{
|
||||||
|
msg = "query failed.";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else //update query
|
||||||
|
{
|
||||||
|
if(ret >= 0)
|
||||||
|
{
|
||||||
|
msg = "update num: " + Util::int2string(ret);
|
||||||
|
}
|
||||||
|
else //update error
|
||||||
|
{
|
||||||
|
msg = "update failed.";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if(ret != -100)
|
||||||
|
{
|
||||||
|
cout << msg << endl;
|
||||||
|
}
|
||||||
|
|
||||||
//test...
|
//test...
|
||||||
//string answer_file = query_file+".out";
|
//string answer_file = query_file+".out";
|
||||||
//Util::save_to_file(answer_file.c_str(), _rs.to_str());
|
//Util::save_to_file(answer_file.c_str(), _rs.to_str());
|
||||||
|
@ -255,4 +324,4 @@ main(int argc, char * argv[])
|
||||||
#endif // READLINE_ON
|
#endif // READLINE_ON
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
|
@ -35,7 +35,7 @@ int main(int argc, char* argv[])
|
||||||
}
|
}
|
||||||
|
|
||||||
if (argc > 3 || (argc == 3 && mode != "-p" && mode != "--port")) {
|
if (argc > 3 || (argc == 3 && mode != "-p" && mode != "--port")) {
|
||||||
cerr << "Invalid arguments! Input \"bin/gserver -h\" for help." << endl;
|
cout << "Invalid arguments! Input \"bin/gserver -h\" for help." << endl;
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -61,7 +61,7 @@ int main(int argc, char* argv[])
|
||||||
unsigned short port = Socket::DEFAULT_CONNECT_PORT;
|
unsigned short port = Socket::DEFAULT_CONNECT_PORT;
|
||||||
if (argc == 3) {
|
if (argc == 3) {
|
||||||
if (!Util::isValidPort(string(argv[2]))) {
|
if (!Util::isValidPort(string(argv[2]))) {
|
||||||
cerr << "Invalid port: " << argv[2] << endl;
|
cout << "Invalid port: " << argv[2] << endl;
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
|
@ -72,7 +72,7 @@ int main(int argc, char* argv[])
|
||||||
if (!isOnlyProcess(argv[0])) {
|
if (!isOnlyProcess(argv[0])) {
|
||||||
ofstream out(GSERVER_PORT_SWAP, ios::out);
|
ofstream out(GSERVER_PORT_SWAP, ios::out);
|
||||||
if (!out) {
|
if (!out) {
|
||||||
cerr << "Failed to change port!" << endl;
|
cout << "Failed to change port!" << endl;
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
out << port;
|
out << port;
|
||||||
|
@ -82,7 +82,7 @@ int main(int argc, char* argv[])
|
||||||
}
|
}
|
||||||
ofstream out(GSERVER_PORT_FILE, ios::out);
|
ofstream out(GSERVER_PORT_FILE, ios::out);
|
||||||
if (!out) {
|
if (!out) {
|
||||||
cerr << "Failed to change port!" << endl;
|
cout << "Failed to change port!" << endl;
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
out << port;
|
out << port;
|
||||||
|
@ -93,7 +93,7 @@ int main(int argc, char* argv[])
|
||||||
|
|
||||||
if (mode == "-s" || mode == "--start") {
|
if (mode == "-s" || mode == "--start") {
|
||||||
if (!isOnlyProcess(argv[0])) {
|
if (!isOnlyProcess(argv[0])) {
|
||||||
cerr << "gServer already running!" << endl;
|
cout << "gServer already running!" << endl;
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
if (startServer()) {
|
if (startServer()) {
|
||||||
|
@ -106,7 +106,7 @@ int main(int argc, char* argv[])
|
||||||
|
|
||||||
if (mode == "-t" || mode == "--stop") {
|
if (mode == "-t" || mode == "--stop") {
|
||||||
if (isOnlyProcess(argv[0])) {
|
if (isOnlyProcess(argv[0])) {
|
||||||
cerr << "gServer not running!" << endl;
|
cout << "gServer not running!" << endl;
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
if (stopServer()) {
|
if (stopServer()) {
|
||||||
|
@ -119,7 +119,7 @@ int main(int argc, char* argv[])
|
||||||
|
|
||||||
if (mode == "-r" || mode == "--restart") {
|
if (mode == "-r" || mode == "--restart") {
|
||||||
if (isOnlyProcess(argv[0])) {
|
if (isOnlyProcess(argv[0])) {
|
||||||
cerr << "gServer not running!" << endl;
|
cout << "gServer not running!" << endl;
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
if (!stopServer()) {
|
if (!stopServer()) {
|
||||||
|
@ -153,14 +153,14 @@ int main(int argc, char* argv[])
|
||||||
|
|
||||||
if (mode == "-k" || mode == "--kill") {
|
if (mode == "-k" || mode == "--kill") {
|
||||||
if (isOnlyProcess(argv[0])) {
|
if (isOnlyProcess(argv[0])) {
|
||||||
cerr << "No process to kill!" << endl;
|
cout << "No process to kill!" << endl;
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
execl("/usr/bin/killall", "killall", Util::getExactPath(argv[0]).c_str(), NULL);
|
execl("/usr/bin/killall", "killall", Util::getExactPath(argv[0]).c_str(), NULL);
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
cerr << "Invalid arguments! Input \"bin/gserver -h\" for help." << endl;
|
cout << "Invalid arguments! Input \"bin/gserver -h\" for help." << endl;
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -174,7 +174,7 @@ void checkSwap() {
|
||||||
}
|
}
|
||||||
ifstream in(GSERVER_PORT_SWAP, ios::in);
|
ifstream in(GSERVER_PORT_SWAP, ios::in);
|
||||||
if (!in) {
|
if (!in) {
|
||||||
cerr << "Failed in checkSwap(), port may not be changed." << endl;
|
cout << "Failed in checkSwap(), port may not be changed." << endl;
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
unsigned short port;
|
unsigned short port;
|
||||||
|
@ -182,7 +182,7 @@ void checkSwap() {
|
||||||
in.close();
|
in.close();
|
||||||
ofstream out(GSERVER_PORT_FILE, ios::out);
|
ofstream out(GSERVER_PORT_FILE, ios::out);
|
||||||
if (!out) {
|
if (!out) {
|
||||||
cerr << "Failed in checkSwap(), port may not be changed." << endl;
|
cout << "Failed in checkSwap(), port may not be changed." << endl;
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
out << port;
|
out << port;
|
||||||
|
@ -219,7 +219,7 @@ bool startServer() {
|
||||||
freopen(GSERVER_LOG, "a", stderr);
|
freopen(GSERVER_LOG, "a", stderr);
|
||||||
Server server(port);
|
Server server(port);
|
||||||
if (!server.createConnection()) {
|
if (!server.createConnection()) {
|
||||||
cerr << Util::getTimeString() << "Failed to create connection at port " << port << '.' << endl;
|
cout << Util::getTimeString() << "Failed to create connection at port " << port << '.' << endl;
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
cout << Util::getTimeString() << "Server started at port " << port << '.' << endl;
|
cout << Util::getTimeString() << "Server started at port " << port << '.' << endl;
|
||||||
|
@ -234,7 +234,7 @@ bool startServer() {
|
||||||
}
|
}
|
||||||
// fork failure
|
// fork failure
|
||||||
else {
|
else {
|
||||||
cerr << "Failed to start server at port " << port << '.' << endl;
|
cout << "Failed to start server at port " << port << '.' << endl;
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -248,17 +248,17 @@ bool stopServer() {
|
||||||
}
|
}
|
||||||
Socket socket;
|
Socket socket;
|
||||||
if (!socket.create() || !socket.connect("127.0.0.1", port) || !socket.send("stop")) {
|
if (!socket.create() || !socket.connect("127.0.0.1", port) || !socket.send("stop")) {
|
||||||
cerr << "Failed to stop server at port " << port << '.' << endl;
|
cout << "Failed to stop server at port " << port << '.' << endl;
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
string recv_msg;
|
string recv_msg;
|
||||||
socket.recv(recv_msg);
|
socket.recv(recv_msg);
|
||||||
socket.close();
|
socket.close();
|
||||||
if (recv_msg != "server stopped.") {
|
if (recv_msg != "server stopped.") {
|
||||||
cerr << "Failed to stop server at port " << port << '.' << endl;
|
cout << "Failed to stop server at port " << port << '.' << endl;
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
cout << "Server stopped at port " << port << '.' << endl;
|
cout << "Server stopped at port " << port << '.' << endl;
|
||||||
checkSwap();
|
checkSwap();
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
148
NOTES.md
148
NOTES.md
|
@ -1,38 +1,95 @@
|
||||||
|
# NOTICE
|
||||||
|
|
||||||
|
一般在实践应用中不是单机,而是CS模式,因为API也是基于CS模式的。
|
||||||
|
那么在CS模式中,可以禁用server端对query结果的输出,提升效率
|
||||||
|
方式是控制Util/Util.h中OUTPUT_QUERY_RESULT宏的开启
|
||||||
|
|
||||||
|
在使用gserver时,不能在数据库没有unload时再用gbuild或其他命令修改数据库,仅限于C/S模式
|
||||||
|
|
||||||
# TODO
|
# TODO
|
||||||
|
|
||||||
gclient 不能正常使用
|
成组插删还没完全支持和测试,需要修改KVstore.cpp
|
||||||
gserver for multiple users, not load db for each connection, but get the db pointer
|
|
||||||
assign the pointer to the user who require this db, and ensure that each db is just kept once in memory
|
|
||||||
|
|
||||||
支持返回?p结果的查询
|
gstore后续需要开发的地方:
|
||||||
辛雨非的插入时vstree bug和彭鹏的build时vstree bug
|
数据库连接池 保持连接而不是每次都用socket
|
||||||
vstree部分在build和insert时候的错误
|
事务操作
|
||||||
统计74上的8亿测试结果
|
安全备份 数据库的多版本备份,动态删除
|
||||||
控制台命令如果使用方式不当,比如直接gbuild,应该输出提示信息示意该怎么操作
|
多领域多库解决方案。
|
||||||
数据库的多版本备份,动态删除
|
分页查询
|
||||||
保持连接而不是每次都用socket
|
|
||||||
模仿海量图大作业,基于gStore开发一个社交应用,要求可以批量导入且实时查询
|
任务分配:
|
||||||
|
---
|
||||||
|
JSON格式传输(陈佳棋)
|
||||||
陈佳棋的任务:s和p对应同一个实体,应该先重命名,再过滤。还有一种情况是两者只是名字相同,实则并无关系
|
陈佳棋的任务:s和p对应同一个实体,应该先重命名,再过滤。还有一种情况是两者只是名字相同,实则并无关系
|
||||||
|
---
|
||||||
|
陈佳棋找人负责:
|
||||||
|
模仿海量图大作业,基于gStore开发一个社交应用,要求可以批量导入且实时查询
|
||||||
|
查询级别的缓存(测试时可将查询复制后再随机打乱)
|
||||||
|
多查询优化
|
||||||
|
---
|
||||||
|
王力博:
|
||||||
|
gserver for multiple users, not load db for each connection, but get the same db pointer
|
||||||
|
assign the pointer to the user who require this db, and ensure that each db is just kept once in memory
|
||||||
|
有什么办法去检测一个db是否存在呢?(首先要支持导入多个数据库)
|
||||||
|
如果不存在 就新建一个 再进行查询 如果存在 就直接进行查询
|
||||||
|
gserver-gclient if gclient quit(without unload), then restart, there maybe exist too many gserver process(so 3305 is occupied)
|
||||||
|
or the reason maybe gserver still dealing with the previous job, then a new connection and a new job comes
|
||||||
|
如何避免整个server崩溃或卡死,无论单个查询/建立等操作遇到任何问题
|
||||||
|
---
|
||||||
|
胡琳:
|
||||||
|
彭鹏师兄的数据集bug
|
||||||
|
优化谓词查询,谓词少而entity/literal多,所以先过滤得到谓词的解是一种可以考虑的策略
|
||||||
|
以谓词为节点,以s/o为信息,来过滤得到谓词的结果
|
||||||
|
---
|
||||||
|
陈语嫣,李荆
|
||||||
|
---
|
||||||
|
张雨的任务:单起点单终点的正则表达式路径问题,如果是多起点多终点?
|
||||||
|
下学期的任务:提取相关联的几个方向写论文
|
||||||
|
将IRC聊天放到gstore文档上,freenode #gStore
|
||||||
|
|
||||||
|
WARN:B+树删除时,向旁边兄弟借或者合并,要注意兄弟的定义,应该是同一父节点才对!
|
||||||
|
考虑使用 sigmod2016 那篇图同构的论文方法,实现一套join
|
||||||
|
但那个是基于路径的,BFS和索引连接的思想值得借用,可作为另外一套join方法
|
||||||
|
@hulin
|
||||||
|
---
|
||||||
|
实现其他的join思路,比如基于过滤效果
|
||||||
|
|
||||||
|
pthread写多线程
|
||||||
|
|
||||||
|
如何在preFilter和join的开销之间做平衡
|
||||||
|
preFilter中的限制条件是否过于严格
|
||||||
|
|
||||||
|
寻找查询图的特征,分类做查询计划:
|
||||||
|
先对于每个查询,确定各部分的开销比例
|
||||||
|
|
||||||
|
fix the full_test:how to sum the db size right?
|
||||||
|
for virtuoso, better to reset each time and the given configure file(need to reserver the temp logs)
|
||||||
|
|
||||||
|
load过程先导入满足内存的内容,或者先来几轮搜索但不输出结果,避免开头的查询要读磁盘。vstree直接全导入内存?
|
||||||
|
先完成合并测试,再测lubm500M和bsbm500M -- 90 server
|
||||||
|
|
||||||
|
两表拼接时多线程分块join
|
||||||
|
jemalloc??
|
||||||
|
vstree并行分块
|
||||||
|
|
||||||
|
|
||||||
|
@lijing
|
||||||
|
考虑出入度数,编码为1的个数?应该不用,在编码的邻居信息中能够得到体现。
|
||||||
|
第二步编码应该更长,点和边对应着放在一起。按出入边分区,一步点,二步边分区和二步点。
|
||||||
|
对一个节点保留其最长链信息没啥用,因为数据图基本是连通的,最长链就是图的最长链。
|
||||||
|
多步编码不应分开,而应在编码逐一扩展,第二步可以依旧保留详细信息,最好用更长编码,因为信息更多。
|
||||||
|
可能有相同的谓词对应多个邻居,同样的谓词只要保留一个即可,不同邻居可以重合。
|
||||||
|
第三步可以只记谓词,第四步可以只记边的出入向。
|
||||||
|
|
||||||
各版本对比的表格中应加一列几何平均数,现实中大多数查询是简单查询,最好还有一个平均数,对应着把数据做归一化后求和
|
各版本对比的表格中应加一列几何平均数,现实中大多数查询是简单查询,最好还有一个平均数,对应着把数据做归一化后求和
|
||||||
dbpedia q6现在应该统计并对比结果了,包含在测试结果中
|
dbpedia q6现在应该统计并对比结果了,包含在测试结果中
|
||||||
|
|
||||||
最好用json格式来输出结果,或者在JSON和字符串之间相互转换
|
在改善kvstore后,build过程明显加快了很多,现在vstree的建立时间成了瓶颈
|
||||||
另外在改善kvstore后,build过程明显加快了很多,现在vstree的建立时间成了瓶颈
|
|
||||||
|
|
||||||
preFilter中不仅要看谓词,也要看表大小以及度数,有些节点最好过滤!!!
|
preFilter中不仅要看谓词,也要看表大小以及度数,有些节点最好过滤!!!
|
||||||
|
|
||||||
在0.4.0版本后统一使用git管理,为各位开发者维护一个分支
|
允许同时使用多个数据库,查询时指明数据库,这样的话可以支持from,但各个数据库是相互独立的;
|
||||||
更新github上的测试报告和help文档
|
添加scala API;
|
||||||
5亿+bug,最好单机能支持到10亿
|
git管理开发;
|
||||||
---
|
|
||||||
备份原来的代码后,合并王的代码并测试,再在原来代码上加join缓存测试
|
|
||||||
以后统一用git进行版本管理,以当前版本为基础
|
|
||||||
bookug, hulin, wlb, cjq, pp, gpu, wuda, chenyuyan各一个分支
|
|
||||||
|
|
||||||
张雨的任务:单起点单终点的正则表达式路径问题,如果是多起点多终点?
|
|
||||||
下学期的任务:提取相关联的几个方向写论文
|
|
||||||
将IRC聊天放到gstore文档上,freenode #gStore
|
|
||||||
|
|
||||||
从下往上建立B+树和vstree树
|
从下往上建立B+树和vstree树
|
||||||
加快更新操作,如insert和delete等,是否考虑增加修改的源操作
|
加快更新操作,如insert和delete等,是否考虑增加修改的源操作
|
||||||
|
@ -49,50 +106,11 @@ bookug, hulin, wlb, cjq, pp, gpu, wuda, chenyuyan各一个分支
|
||||||
但机器学习对新问题没有一个基本的界,不像数学化的评估函数,对任何情况都能保证一个上界
|
但机器学习对新问题没有一个基本的界,不像数学化的评估函数,对任何情况都能保证一个上界
|
||||||
(目前数据库里面很少有人利用机器学习来估价)
|
(目前数据库里面很少有人利用机器学习来估价)
|
||||||
|
|
||||||
WARN:B+树删除时,向旁边兄弟借或者合并,要注意兄弟的定义,应该是同一父节点才对!
|
|
||||||
输出还是组织成JSON格式比较好,用JSON的C++库进行压缩解压,客户端也无需对输出格式有太多了解,减轻后者负担
|
|
||||||
|
|
||||||
URI是唯一的,RDF图中不存在相同标签的节点,无法合并相似节点,也没法利用自同构的预处理加快查询
|
URI是唯一的,RDF图中不存在相同标签的节点,无法合并相似节点,也没法利用自同构的预处理加快查询
|
||||||
DBpedia最新的数据集,原来的相对太小了
|
DBpedia最新的数据集,原来的相对太小了
|
||||||
count函数的优化:深搜计数即可,不必生成中间表
|
count函数的优化:深搜计数即可,不必生成中间表
|
||||||
B+树每个节点内部添加索引,对keys分段?
|
B+树每个节点内部添加索引,对keys分段?
|
||||||
|
|
||||||
考虑使用 sigmod2016 那篇图同构的论文方法,实现一套join
|
|
||||||
但那个是基于路径的,BFS和索引连接的思想值得借用,可作为另外一套join方法
|
|
||||||
@hulin
|
|
||||||
---
|
|
||||||
实现其他的join思路,比如基于过滤效果
|
|
||||||
|
|
||||||
pthread写多线程
|
|
||||||
可以尝试开-O6优化,如果结果保证正确,应该速度可以提升很多
|
|
||||||
@lijing
|
|
||||||
验证-O6的正确性和效率
|
|
||||||
|
|
||||||
如何在preFilter和join的开销之间做平衡
|
|
||||||
preFilter中的限制条件是否过于严格
|
|
||||||
|
|
||||||
寻找查询图的特征,分类做查询计划:
|
|
||||||
先对于每个查询,确定各部分的开销比例
|
|
||||||
|
|
||||||
fix the full_test:how to sum the db size right?
|
|
||||||
for virtuoso, better to reset each time and the given configure file(need to reserver the temp logs)
|
|
||||||
|
|
||||||
load过程先导入满足内存的内容,或者先来几轮搜索但不输出结果,避免开头的查询要读磁盘。vstree直接全导入内存?
|
|
||||||
先完成合并测试,再测lubm500M和bsbm500M -- 90 server
|
|
||||||
|
|
||||||
两表拼接时多线程分块join
|
|
||||||
jemalloc??
|
|
||||||
查询级别的缓存(测试时可将查询复制后再随机打乱)
|
|
||||||
vstree并行分块
|
|
||||||
|
|
||||||
|
|
||||||
@lijing
|
|
||||||
考虑出入度数,编码为1的个数?应该不用,在编码的邻居信息中能够得到体现。
|
|
||||||
第二步编码应该更长,点和边对应着放在一起。按出入边分区,一步点,二步边分区和二步点。
|
|
||||||
对一个节点保留其最长链信息没啥用,因为数据图基本是连通的,最长链就是图的最长链。
|
|
||||||
多步编码不应分开,而应在编码逐一扩展,第二步可以依旧保留详细信息,最好用更长编码,因为信息更多。
|
|
||||||
可能有相同的谓词对应多个邻居,同样的谓词只要保留一个即可,不同邻居可以重合。
|
|
||||||
第三步可以只记谓词,第四步可以只记边的出入向。
|
|
||||||
|
|
||||||
是否可以考虑把literal也作为vstree中的节点,加快过滤?
|
是否可以考虑把literal也作为vstree中的节点,加快过滤?
|
||||||
join过程中生成literal可能开销大,且可以考虑用周围边对literal进行过滤。。。
|
join过程中生成literal可能开销大,且可以考虑用周围边对literal进行过滤。。。
|
||||||
|
@ -365,7 +383,7 @@ http://www.oschina.net/question/188977_58777
|
||||||
|
|
||||||
- 新算法在冷启动时时间不理想,即便只是0轮join开销也很大,对比时采用热启动
|
- 新算法在冷启动时时间不理想,即便只是0轮join开销也很大,对比时采用热启动
|
||||||
|
|
||||||
- 不能支持非连通图查询(应该分割为多个连通图)
|
- 如果select中某变量未出现在查询图中,应该对该变量返回空值还是直接认为该查询非法
|
||||||
|
|
||||||
- - -
|
- - -
|
||||||
|
|
||||||
|
|
|
@ -141,20 +141,33 @@ BasicQuery::getVarDegree(int _var)
|
||||||
|
|
||||||
//get the index of edge between two var ids
|
//get the index of edge between two var ids
|
||||||
//-1 if no edge, the index is based on _id0
|
//-1 if no edge, the index is based on _id0
|
||||||
int
|
vector<int>
|
||||||
BasicQuery::getEdgeIndex(int _id0, int _id)
|
BasicQuery::getEdgeIndex(int _id0, int _id)
|
||||||
{
|
{
|
||||||
//BETTER:this a brute-force method, using mapping if needed
|
//BETTER:this a brute-force method, using mapping if needed
|
||||||
//(though the query graph is small generally)
|
//(though the query graph is small generally)
|
||||||
//is there any way to pre-compute all EdgeIndex relationship
|
//is there any way to pre-compute all EdgeIndex relationship
|
||||||
|
|
||||||
|
vector<int> result;
|
||||||
for(int i = 0; i < this->var_degree[_id0]; ++i)
|
for(int i = 0; i < this->var_degree[_id0]; ++i)
|
||||||
{
|
{
|
||||||
if(this->edge_nei_id[_id0][i] == _id)
|
if(this->edge_nei_id[_id0][i] == _id)
|
||||||
{
|
{
|
||||||
return i;
|
//NOTICE:maybe exist parallel edges i.e.
|
||||||
|
//?s ?p1 ?o. ?s ?p2 ?o.
|
||||||
|
//?s p1 ?o. ?s p2 ?o.
|
||||||
|
//return i;
|
||||||
|
|
||||||
|
//if(this->getEdgePreID(_id0, i) < 0)
|
||||||
|
//{
|
||||||
|
//continue;
|
||||||
|
//}
|
||||||
|
result.push_back(i);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return -1;
|
|
||||||
|
//return -1;
|
||||||
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
//get the candidate list of _var in the query graph
|
//get the candidate list of _var in the query graph
|
||||||
|
@ -274,7 +287,10 @@ BasicQuery::isFreeLiteralVariable(int _var)
|
||||||
int neighbor_num = this->var_degree[_var];
|
int neighbor_num = this->var_degree[_var];
|
||||||
for(int i = 0; i < neighbor_num; i ++)
|
for(int i = 0; i < neighbor_num; i ++)
|
||||||
{
|
{
|
||||||
if(this->edge_nei_id[_var][i] == -1)
|
int triple_id = this->getEdgeID(_var, i);
|
||||||
|
Triple triple = this->getTriple(triple_id);
|
||||||
|
//NOTICE: the neighbor can also be a var whose id is -1
|
||||||
|
if(triple.subject[0] != '?')
|
||||||
{
|
{
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
@ -379,13 +395,8 @@ bool
|
||||||
BasicQuery::encodeBasicQuery(KVstore* _p_kvstore, const vector<string>& _query_var)
|
BasicQuery::encodeBasicQuery(KVstore* _p_kvstore, const vector<string>& _query_var)
|
||||||
{
|
{
|
||||||
//WARN:?p is ok to exist in both s/o or p position
|
//WARN:?p is ok to exist in both s/o or p position
|
||||||
//return only the entity ID, not the predicate ID
|
//TODO:return only the entity ID, not the predicate ID?
|
||||||
//so the _query_var mix all the variables, not considering the order
|
//so the _query_var mix all the variables, not considering the order
|
||||||
//
|
|
||||||
//TODO:the third parameter should be selected predicate variables
|
|
||||||
//(ordered, and merged with selected s/o in upper level)
|
|
||||||
//we append the candidates for selected pre_var to original select_var_num columns
|
|
||||||
//TODO:add pre var, assign name and select=true (not disturb the order between pres)
|
|
||||||
cout << "IN buildBasicSignature" << endl;
|
cout << "IN buildBasicSignature" << endl;
|
||||||
//this->initial();
|
//this->initial();
|
||||||
//cout << "after init" << endl;
|
//cout << "after init" << endl;
|
||||||
|
@ -395,20 +406,58 @@ BasicQuery::encodeBasicQuery(KVstore* _p_kvstore, const vector<string>& _query_v
|
||||||
// map id 2 var_name : this->var_name[]
|
// map id 2 var_name : this->var_name[]
|
||||||
// map var_name 2 id : this->var_str2id
|
// map var_name 2 id : this->var_str2id
|
||||||
|
|
||||||
this->select_var_num = _query_var.size();
|
//find all predicate vars
|
||||||
|
for(unsigned i = 0; i < this->triple_vt.size(); i ++)
|
||||||
|
{
|
||||||
|
string& pre = this->triple_vt[i].predicate;
|
||||||
|
if(pre[0] != '?')
|
||||||
|
{
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
string& sub = this->triple_vt[i].subject;
|
||||||
|
string& obj = this->triple_vt[i].object;
|
||||||
|
int pid = this->getPreVarID(pre);
|
||||||
|
if(pid == -1)
|
||||||
|
{
|
||||||
|
this->pre_var.push_back(PreVar(pre));
|
||||||
|
pid = this->pre_var.size() - 1;
|
||||||
|
}
|
||||||
|
//map<int, PreVar>::iterator it = this->pre_var.find(pid);
|
||||||
|
//it->second.triples.push_back(i);
|
||||||
|
this->pre_var[pid].triples.push_back(i);
|
||||||
|
}
|
||||||
|
|
||||||
|
//NOTICE: we append the candidates for selected pre_var to original select_var_num columns
|
||||||
|
this->select_var_num = this->selected_pre_var_num = 0;
|
||||||
|
cout<<"now to check the query var list order:"<<endl;
|
||||||
|
for(unsigned i = 0; i < _query_var.size(); ++i)
|
||||||
|
{
|
||||||
|
//NOTICE:not place pre var in join
|
||||||
|
string var = _query_var[i];
|
||||||
|
cout<<i<<" "<<var<<endl;
|
||||||
|
int pid = this->getPreVarID(var);
|
||||||
|
if(pid == -1) // not pre var
|
||||||
|
{
|
||||||
|
this->selected_var_set.insert(var);
|
||||||
|
//assign id for this var
|
||||||
|
int id = this->select_var_num;
|
||||||
|
this->selected_var_position[id] = i;
|
||||||
|
this->var_str2id[var] = id;
|
||||||
|
this->var_name[id] = var;
|
||||||
|
this->select_var_num++;
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
this->selected_var_position[-1-pid] = i;
|
||||||
|
this->pre_var[pid].selected = true;
|
||||||
|
this->selected_pre_var_num++;
|
||||||
|
}
|
||||||
|
|
||||||
#ifdef DEBUG
|
#ifdef DEBUG
|
||||||
stringstream _ss;
|
stringstream _ss;
|
||||||
_ss << "select_var_num=" << this->select_var_num << endl;
|
_ss << "select_var_num=" << this->select_var_num << endl;
|
||||||
Util::logging(_ss.str());
|
Util::logging(_ss.str());
|
||||||
#endif
|
#endif
|
||||||
for(int i = 0; i < (this->select_var_num); ++i)
|
|
||||||
{
|
|
||||||
//NOTICE:not place pre var in join
|
|
||||||
string _var = _query_var[i];
|
|
||||||
this->var_str2id[_var] = i;
|
|
||||||
this->var_name[i] = _var;
|
|
||||||
}
|
|
||||||
|
|
||||||
cout << "select variables: ";
|
cout << "select variables: ";
|
||||||
for(unsigned i = 0; i < this->var_str2id.size(); ++i)
|
for(unsigned i = 0; i < this->var_str2id.size(); ++i)
|
||||||
|
@ -416,6 +465,7 @@ BasicQuery::encodeBasicQuery(KVstore* _p_kvstore, const vector<string>& _query_v
|
||||||
cout << "[" << this->var_name[i] << ", " << i << " " << this->var_str2id[this->var_name[i]] << "]\t";
|
cout << "[" << this->var_name[i] << ", " << i << " " << this->var_str2id[this->var_name[i]] << "]\t";
|
||||||
}
|
}
|
||||||
cout << endl;
|
cout << endl;
|
||||||
|
//BETTER:ouput the selected pre vars
|
||||||
|
|
||||||
this->total_var_num = this->select_var_num;
|
this->total_var_num = this->select_var_num;
|
||||||
if(this->encode_method == BasicQuery::SELECT_VAR)
|
if(this->encode_method == BasicQuery::SELECT_VAR)
|
||||||
|
@ -444,20 +494,10 @@ BasicQuery::encodeBasicQuery(KVstore* _p_kvstore, const vector<string>& _query_v
|
||||||
string& sub = this->triple_vt[i].subject;
|
string& sub = this->triple_vt[i].subject;
|
||||||
string& pre = this->triple_vt[i].predicate;
|
string& pre = this->triple_vt[i].predicate;
|
||||||
string& obj = this->triple_vt[i].object;
|
string& obj = this->triple_vt[i].object;
|
||||||
|
|
||||||
int pre_id = -1; //not found
|
int pre_id = -1; //not found
|
||||||
if(pre[0] == '?') //pre var
|
if(pre[0] == '?') //pre var
|
||||||
{
|
{
|
||||||
int pid = this->getPreVarID(pre);
|
|
||||||
if(pid == -1)
|
|
||||||
{
|
|
||||||
//pid = this->select_var_num + this->pre_var.size();
|
|
||||||
//this->pre_var[pid] = PreVar(pre);
|
|
||||||
this->pre_var.push_back(PreVar(pre));
|
|
||||||
pid = this->pre_var.size() - 1;
|
|
||||||
}
|
|
||||||
//map<int, PreVar>::iterator it = this->pre_var.find(pid);
|
|
||||||
//it->second.triples.push_back(i);
|
|
||||||
this->pre_var[pid].triples.push_back(i);
|
|
||||||
pre_id = -2; //mark that this is a pre var
|
pre_id = -2; //mark that this is a pre var
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
|
@ -469,18 +509,15 @@ BasicQuery::encodeBasicQuery(KVstore* _p_kvstore, const vector<string>& _query_v
|
||||||
_ss << "pre2id: " << pre << "=>" << pre_id << endl;
|
_ss << "pre2id: " << pre << "=>" << pre_id << endl;
|
||||||
Util::logging(_ss.str());
|
Util::logging(_ss.str());
|
||||||
}
|
}
|
||||||
if(pre_id == -1)
|
|
||||||
{
|
|
||||||
//TODO:end this query, otherwise maybe error later
|
|
||||||
cerr << "invalid query because the pre is not found: " << pre << endl;
|
|
||||||
//BETTER:this is too robust, not only one query, try return false
|
|
||||||
//exit(1);
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
if(pre_id == -1)
|
||||||
|
{
|
||||||
|
cout << "invalid query because the pre is not found: " << pre << endl;
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
int sub_id = -1;
|
int sub_id = -1;
|
||||||
int obj_id = -1;
|
int obj_id = -1;
|
||||||
|
|
||||||
// -1 if not found, this means this subject is a constant
|
// -1 if not found, this means this subject is a constant
|
||||||
map<string, int>::iterator _find_sub_itr = (this->var_str2id).find(sub);
|
map<string, int>::iterator _find_sub_itr = (this->var_str2id).find(sub);
|
||||||
if(_find_sub_itr != this->var_str2id.end())
|
if(_find_sub_itr != this->var_str2id.end())
|
||||||
|
@ -555,12 +592,110 @@ BasicQuery::encodeBasicQuery(KVstore* _p_kvstore, const vector<string>& _query_v
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int
|
||||||
|
BasicQuery::getSelectedVarPosition(int _var)
|
||||||
|
{
|
||||||
|
map<int, int>::iterator it = this->selected_var_position.find(_var);
|
||||||
|
if(it == this->selected_var_position.end())
|
||||||
|
{
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
return it->second;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
int
|
||||||
|
BasicQuery::getSelectedPreVarPosition(int _var)
|
||||||
|
{
|
||||||
|
//change var to -1-var to avoid conflicting with normal var
|
||||||
|
map<int, int>::iterator it = this->selected_var_position.find(-1-_var);
|
||||||
|
if(it == this->selected_var_position.end())
|
||||||
|
{
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
return it->second;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
int
|
||||||
|
BasicQuery::getSelectedVarPosition(string _var)
|
||||||
|
{
|
||||||
|
int id = this->getIDByVarName(_var);
|
||||||
|
if(id < 0)
|
||||||
|
{
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
map<int, int>::iterator it = this->selected_var_position.find(id);
|
||||||
|
if(it == this->selected_var_position.end())
|
||||||
|
{
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
return it->second;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
int
|
||||||
|
BasicQuery::getSelectedPreVarPosition(string _var)
|
||||||
|
{
|
||||||
|
int id = this->getPreVarID(_var);
|
||||||
|
if(id < 0)
|
||||||
|
{
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
//change var to -1-var to avoid conflicting with normal var
|
||||||
|
map<int, int>::iterator it = this->selected_var_position.find(-1-id);
|
||||||
|
if(it == this->selected_var_position.end())
|
||||||
|
{
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
return it->second;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
bool
|
bool
|
||||||
BasicQuery::getEncodeBasicQueryResult() const
|
BasicQuery::getEncodeBasicQueryResult() const
|
||||||
{
|
{
|
||||||
return this->encode_result;
|
return this->encode_result;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int
|
||||||
|
BasicQuery::getIDByVarName(const string& _name)
|
||||||
|
{
|
||||||
|
map<string,int>::iterator it = this->var_str2id.find(_name);
|
||||||
|
if(it != this->var_str2id.end())
|
||||||
|
{
|
||||||
|
return it->second;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
//WARN:if return var_str2id[_name] directly, this will be 0
|
||||||
|
//maybe conflict with valid ID 0
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
bool
|
||||||
|
BasicQuery::isVarSelected(const string& _name) const
|
||||||
|
{
|
||||||
|
set<string>::iterator it = this->selected_var_set.find(_name);
|
||||||
|
if(it == this->selected_var_set.end())
|
||||||
|
{
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
int
|
int
|
||||||
BasicQuery::getPreVarID(const string& _name) const
|
BasicQuery::getPreVarID(const string& _name) const
|
||||||
{
|
{
|
||||||
|
@ -589,27 +724,17 @@ BasicQuery::getPreVarByID(unsigned _id) const
|
||||||
else
|
else
|
||||||
return this->pre_var[0];
|
return this->pre_var[0];
|
||||||
}
|
}
|
||||||
|
unsigned
|
||||||
//int
|
BasicQuery::getSelectedPreVarNum() const
|
||||||
//BasicQuery::getIDByPreVarName(const string& _name) const
|
|
||||||
//{
|
|
||||||
//return 0;
|
|
||||||
//}
|
|
||||||
|
|
||||||
int
|
|
||||||
BasicQuery::getIDByVarName(const string& _name)
|
|
||||||
{
|
{
|
||||||
map<string,int>::iterator it = this->var_str2id.find(_name);
|
return this->selected_pre_var_num;
|
||||||
if(it != this->var_str2id.end())
|
}
|
||||||
{
|
|
||||||
return it->second;
|
bool
|
||||||
}
|
BasicQuery::isPreVarSelected(unsigned _pid) const
|
||||||
else
|
{
|
||||||
{
|
//BETTER:check if the pid is valid
|
||||||
//WARN:if return var_str2id[_name] directly, this will be 0
|
return this->pre_var[_pid].selected;
|
||||||
//maybe conflict with valid ID 0
|
|
||||||
return -1;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
|
@ -628,7 +753,6 @@ BasicQuery::getTriple(int _i_th_triple)
|
||||||
void
|
void
|
||||||
BasicQuery::null_initial()
|
BasicQuery::null_initial()
|
||||||
{
|
{
|
||||||
this->option_vs.clear();
|
|
||||||
this->triple_vt.clear();
|
this->triple_vt.clear();
|
||||||
this->var_str2id.clear();
|
this->var_str2id.clear();
|
||||||
this->var_degree = NULL;
|
this->var_degree = NULL;
|
||||||
|
|
|
@ -102,17 +102,17 @@ public:
|
||||||
class BasicQuery
|
class BasicQuery
|
||||||
{
|
{
|
||||||
private:
|
private:
|
||||||
vector<string> option_vs;
|
|
||||||
vector<Triple> triple_vt;
|
vector<Triple> triple_vt;
|
||||||
// mapping from variables' name to their assigned id
|
// mapping from variables' name to their assigned id
|
||||||
map<std::string, int> var_str2id;
|
map<std::string, int> var_str2id;
|
||||||
// record each tuple's(subject, predicate, object) number of occurrences in this BasicQuery
|
// record each tuple's(subject, predicate, object) number of occurrences in this BasicQuery
|
||||||
map<std::string, int> tuple2freq;
|
map<std::string, int> tuple2freq;
|
||||||
|
set<std::string> selected_var_set;
|
||||||
|
//NOTICE:this is not used now!
|
||||||
map<std::string, int> var_not_in_select;
|
map<std::string, int> var_not_in_select;
|
||||||
|
|
||||||
// id < select_var_num means in select
|
// id < select_var_num means in select
|
||||||
int select_var_num;
|
int select_var_num;
|
||||||
|
|
||||||
// var_num is different from that in SPARQLquery
|
// var_num is different from that in SPARQLquery
|
||||||
// because there are some variable not in select
|
// because there are some variable not in select
|
||||||
int graph_var_num;
|
int graph_var_num;
|
||||||
|
@ -165,6 +165,12 @@ private:
|
||||||
|
|
||||||
//infos for predicate variables
|
//infos for predicate variables
|
||||||
vector<PreVar> pre_var;
|
vector<PreVar> pre_var;
|
||||||
|
int selected_pre_var_num;
|
||||||
|
|
||||||
|
//to manage the selected vars order(considering selected pre var)
|
||||||
|
//NOTICE:the order is always same as query_var in encodeBasicQuery, but not always same as select-clause
|
||||||
|
//positive key id for normal var, -1-id for pre var
|
||||||
|
map<int, int> selected_var_position;
|
||||||
|
|
||||||
public:
|
public:
|
||||||
static const int MAX_VAR_NUM = 10;
|
static const int MAX_VAR_NUM = 10;
|
||||||
|
@ -192,14 +198,16 @@ public:
|
||||||
// get the name of _var in the query graph
|
// get the name of _var in the query graph
|
||||||
std::string getVarName(int _var);
|
std::string getVarName(int _var);
|
||||||
|
|
||||||
|
int getIDByVarName(const string& _name);
|
||||||
|
|
||||||
// get triples number, also sentences number
|
// get triples number, also sentences number
|
||||||
int getTripleNum();
|
int getTripleNum();
|
||||||
|
|
||||||
int getIDByVarName(const string& _name);
|
//check if a normal var is in select
|
||||||
|
bool isVarSelected(const std::string& _name) const;
|
||||||
|
|
||||||
std::string to_str();
|
std::string to_str();
|
||||||
|
|
||||||
|
|
||||||
// get the ID of the i-th triple
|
// get the ID of the i-th triple
|
||||||
const Triple& getTriple(int _i_th_triple);
|
const Triple& getTriple(int _i_th_triple);
|
||||||
|
|
||||||
|
@ -219,7 +227,7 @@ public:
|
||||||
int getVarDegree(int _var);
|
int getVarDegree(int _var);
|
||||||
|
|
||||||
//get the index of edge between two var ids
|
//get the index of edge between two var ids
|
||||||
int getEdgeIndex(int _id0, int _id);
|
vector<int> getEdgeIndex(int _id0, int _id);
|
||||||
|
|
||||||
const EntityBitSet& getVarBitSet(int _i)const;
|
const EntityBitSet& getVarBitSet(int _i)const;
|
||||||
|
|
||||||
|
@ -269,8 +277,14 @@ public:
|
||||||
|
|
||||||
unsigned getPreVarNum() const;
|
unsigned getPreVarNum() const;
|
||||||
const PreVar& getPreVarByID(unsigned) const;
|
const PreVar& getPreVarByID(unsigned) const;
|
||||||
//int getIDByPreVarName(const std::string& _name) const;
|
|
||||||
int getPreVarID(const string& _name) const;
|
int getPreVarID(const string& _name) const;
|
||||||
|
unsigned getSelectedPreVarNum() const;
|
||||||
|
bool isPreVarSelected(unsigned _pid) const;
|
||||||
|
|
||||||
|
int getSelectedVarPosition(int _var);
|
||||||
|
int getSelectedPreVarPosition(int _var);
|
||||||
|
int getSelectedVarPosition(std::string _var);
|
||||||
|
int getSelectedPreVarPosition(std::string _var);
|
||||||
|
|
||||||
void addTriple(const Triple& _triple);
|
void addTriple(const Triple& _triple);
|
||||||
void print(ostream& _out_stream);
|
void print(ostream& _out_stream);
|
||||||
|
|
|
@ -28,7 +28,7 @@ bool GeneralEvaluation::parseQuery(const string &_query)
|
||||||
}
|
}
|
||||||
catch(const char *e)
|
catch(const char *e)
|
||||||
{
|
{
|
||||||
cerr << e << endl;
|
cout << e << endl;
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -40,25 +40,25 @@ QueryTree& GeneralEvaluation::getQueryTree()
|
||||||
return this->query_tree;
|
return this->query_tree;
|
||||||
}
|
}
|
||||||
|
|
||||||
void GeneralEvaluation::doQuery()
|
bool GeneralEvaluation::doQuery()
|
||||||
{
|
{
|
||||||
if (!this->query_tree.checkProjectionAsterisk() && this->query_tree.getProjection().size() == 0)
|
if (!this->query_tree.checkProjectionAsterisk() && this->query_tree.getProjection().size() == 0)
|
||||||
return;
|
return false;
|
||||||
|
|
||||||
if (!this->query_tree.checkSelectCompatibility())
|
if (!this->query_tree.checkSelectCompatibility())
|
||||||
{
|
{
|
||||||
cerr << "[ERROR] The vars and aggregate functions in the SelectClause are not compatible." << endl;
|
cout << "[ERROR] The vars and aggregate functions in the SelectClause are not compatible." << endl;
|
||||||
return;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
this->query_tree.getGroupPattern().getVarset();
|
this->query_tree.getGroupPattern().getVarset();
|
||||||
if (this->query_tree.getGroupPattern().grouppattern_subject_object_maximal_varset.hasCommonVar(this->query_tree.getGroupPattern().grouppattern_predicate_maximal_varset))
|
if (this->query_tree.getGroupPattern().grouppattern_subject_object_maximal_varset.hasCommonVar(this->query_tree.getGroupPattern().grouppattern_predicate_maximal_varset))
|
||||||
{
|
{
|
||||||
cerr << "[ERROR] There are some vars occur both in subject/object and predicate." << endl;
|
cout << "[ERROR] There are some vars occur both in subject/object and predicate." << endl;
|
||||||
return;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
this->strategy = Strategy(this->kvstore, this->vstree, this->pre2num);
|
this->strategy = Strategy(this->kvstore, this->vstree, this->pre2num, this->limitID_predicate, this->limitID_literal);
|
||||||
if (this->query_tree.checkWellDesigned())
|
if (this->query_tree.checkWellDesigned())
|
||||||
{
|
{
|
||||||
cout << "=================" << endl;
|
cout << "=================" << endl;
|
||||||
|
@ -91,6 +91,8 @@ void GeneralEvaluation::doQuery()
|
||||||
long tv_postproc = Util::get_cur_time();
|
long tv_postproc = Util::get_cur_time();
|
||||||
cout << "after Postprocessing, used " << (tv_postproc - tv_handle) << "ms." << endl;
|
cout << "after Postprocessing, used " << (tv_postproc - tv_handle) << "ms." << endl;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
void GeneralEvaluation::getBasicQuery(QueryTree::GroupPattern &grouppattern)
|
void GeneralEvaluation::getBasicQuery(QueryTree::GroupPattern &grouppattern)
|
||||||
|
@ -2535,6 +2537,8 @@ void GeneralEvaluation::prepareUpdateTriple(QueryTree::GroupPattern &update_patt
|
||||||
object_id = Varset(update_pattern.patterns[i].object.value).mapTo(results_id->results[j].var)[0];
|
object_id = Varset(update_pattern.patterns[i].object.value).mapTo(results_id->results[j].var)[0];
|
||||||
|
|
||||||
string subject, predicate, object;
|
string subject, predicate, object;
|
||||||
|
TripleWithObjType::ObjectType object_type;
|
||||||
|
|
||||||
if (subject_id == -1)
|
if (subject_id == -1)
|
||||||
subject = update_pattern.patterns[i].subject.value;
|
subject = update_pattern.patterns[i].subject.value;
|
||||||
if (predicate_id == -1)
|
if (predicate_id == -1)
|
||||||
|
@ -2550,8 +2554,12 @@ void GeneralEvaluation::prepareUpdateTriple(QueryTree::GroupPattern &update_patt
|
||||||
this->stringindex->randomAccess(results_id->results[j].res[k][predicate_id], &predicate, false);
|
this->stringindex->randomAccess(results_id->results[j].res[k][predicate_id], &predicate, false);
|
||||||
if (object_id != -1)
|
if (object_id != -1)
|
||||||
this->stringindex->randomAccess(results_id->results[j].res[k][object_id], &object, true);
|
this->stringindex->randomAccess(results_id->results[j].res[k][object_id], &object, true);
|
||||||
|
if (object[0] == '<')
|
||||||
|
object_type = TripleWithObjType::Entity;
|
||||||
|
else
|
||||||
|
object_type = TripleWithObjType::Literal;
|
||||||
|
|
||||||
update_triple[update_triple_count++] = TripleWithObjType(subject, predicate, object);
|
update_triple[update_triple_count++] = TripleWithObjType(subject, predicate, object, object_type);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -35,14 +35,16 @@ class GeneralEvaluation
|
||||||
VSTree *vstree;
|
VSTree *vstree;
|
||||||
KVstore *kvstore;
|
KVstore *kvstore;
|
||||||
TNUM* pre2num;
|
TNUM* pre2num;
|
||||||
|
int limitID_predicate;
|
||||||
|
int limitID_literal;
|
||||||
StringIndex *stringindex;
|
StringIndex *stringindex;
|
||||||
Strategy strategy;
|
Strategy strategy;
|
||||||
ResultFilter result_filter;
|
ResultFilter result_filter;
|
||||||
bool need_output_answer;
|
bool need_output_answer;
|
||||||
|
|
||||||
public:
|
public:
|
||||||
explicit GeneralEvaluation(VSTree *_vstree, KVstore *_kvstore, StringIndex *_stringindex, TNUM* _pre2num):
|
explicit GeneralEvaluation(VSTree *_vstree, KVstore *_kvstore, StringIndex *_stringindex, TNUM* _pre2num, int _limitID_predicate, int _limitID_literal):
|
||||||
vstree(_vstree), kvstore(_kvstore), stringindex(_stringindex), pre2num(_pre2num), need_output_answer(false)
|
vstree(_vstree), kvstore(_kvstore), stringindex(_stringindex), pre2num(_pre2num), limitID_predicate(_limitID_predicate), limitID_literal(_limitID_literal), need_output_answer(false)
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -51,7 +53,7 @@ class GeneralEvaluation
|
||||||
bool parseQuery(const std::string &_query);
|
bool parseQuery(const std::string &_query);
|
||||||
QueryTree& getQueryTree();
|
QueryTree& getQueryTree();
|
||||||
|
|
||||||
void doQuery();
|
bool doQuery();
|
||||||
|
|
||||||
void getBasicQuery(QueryTree::GroupPattern &grouppattern);
|
void getBasicQuery(QueryTree::GroupPattern &grouppattern);
|
||||||
|
|
||||||
|
|
|
@ -216,7 +216,7 @@ IDList::intersectList(const int* _id_list, int _list_len)
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
default:
|
default:
|
||||||
cerr << "no such method in IDList::intersectList()" << endl;
|
cout << "no such method in IDList::intersectList()" << endl;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -450,7 +450,7 @@ IDList::intersect(const IDList& _id_list, const int* _list, int _len)
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
default:
|
default:
|
||||||
cerr << "no such method in IDList::intersectList()" << endl;
|
cout << "no such method in IDList::intersectList()" << endl;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -16,7 +16,7 @@ This system is really user-friendly and you can pick it up in several minutes. R
|
||||||
|
|
||||||
- type `git clone git@github.com:Caesar11/gStore.git` in your terminal or use git GUI to acquire it
|
- type `git clone git@github.com:Caesar11/gStore.git` in your terminal or use git GUI to acquire it
|
||||||
|
|
||||||
Then you need to compile the project, just type `make` in the gStore root directory, and all executables will be ok. To run gStore, please type `bin/gload database_name dataset_path` to build a database named by yourself. And you can use `bin/gquery database_name` command to query a existing database. What is more, `bin/gconsole` is a wonderful tool designed for you, providing all operations you need to use gStore. Notice that all commands should be typed in the root directory of gStore, and your database name should not end with ".db".
|
Then you need to compile the project, just type `make` in the gStore root directory, and all executables will be ok. To run gStore, please type `bin/gbuild database_name dataset_path` to build a database named by yourself. And you can use `bin/gquery database_name` command to query a existing database. What is more, `bin/gconsole` is a wonderful tool designed for you, providing all operations you need to use gStore. Notice that all commands should be typed in the root directory of gStore, and your database name should not end with ".db".
|
||||||
|
|
||||||
- - -
|
- - -
|
||||||
|
|
||||||
|
|
|
@ -232,7 +232,6 @@ void Client::run()
|
||||||
{
|
{
|
||||||
cmd = string(buf);
|
cmd = string(buf);
|
||||||
}
|
}
|
||||||
//DEBUG!
|
|
||||||
printf("%s\n", cmd.c_str());
|
printf("%s\n", cmd.c_str());
|
||||||
|
|
||||||
free(buf);
|
free(buf);
|
||||||
|
@ -262,6 +261,7 @@ void Client::run()
|
||||||
|
|
||||||
string recv_msg;
|
string recv_msg;
|
||||||
flag = this->receiveResponse(recv_msg);
|
flag = this->receiveResponse(recv_msg);
|
||||||
|
//BETTER:the string maybe too large?
|
||||||
fprintf(fp, "%s\n", recv_msg.c_str());
|
fprintf(fp, "%s\n", recv_msg.c_str());
|
||||||
|
|
||||||
this->disconnectServer();
|
this->disconnectServer();
|
||||||
|
|
|
@ -165,13 +165,13 @@ Server::listen()
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case CMD_INSERT:
|
//case CMD_INSERT:
|
||||||
{
|
//{
|
||||||
string db_name = operation.getParameter(0);
|
//string db_name = operation.getParameter(0);
|
||||||
string rdf_path = operation.getParameter(1);
|
//string rdf_path = operation.getParameter(1);
|
||||||
this->insertTriple(db_name, "", rdf_path, ret_msg);
|
//this->insertTriple(db_name, "", rdf_path, ret_msg);
|
||||||
break;
|
//break;
|
||||||
}
|
//}
|
||||||
case CMD_STOP:
|
case CMD_STOP:
|
||||||
{
|
{
|
||||||
this->stopServer(ret_msg);
|
this->stopServer(ret_msg);
|
||||||
|
@ -355,7 +355,15 @@ Server::dropDatabase(std::string _db_name, std::string _ac_name, std::string& _r
|
||||||
bool
|
bool
|
||||||
Server::loadDatabase(std::string _db_name, std::string _ac_name, std::string& _ret_msg)
|
Server::loadDatabase(std::string _db_name, std::string _ac_name, std::string& _ret_msg)
|
||||||
{
|
{
|
||||||
this->database = new Database(_db_name);
|
if(this->database == NULL)
|
||||||
|
{
|
||||||
|
this->database = new Database(_db_name);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
_ret_msg = "please unload the current db first: " + this->database->getName();
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
bool flag = this->database->load();
|
bool flag = this->database->load();
|
||||||
|
|
||||||
|
@ -416,29 +424,29 @@ Server::importRDF(std::string _db_name, std::string _ac_name, std::string _rdf_p
|
||||||
return flag;
|
return flag;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool
|
//bool
|
||||||
Server::insertTriple(std::string _db_name, std::string _ac_name, std::string _rdf_path, std::string& _ret_msg)
|
//Server::insertTriple(std::string _db_name, std::string _ac_name, std::string _rdf_path, std::string& _ret_msg)
|
||||||
{
|
//{
|
||||||
if (this->database != NULL)
|
//if (this->database != NULL)
|
||||||
{
|
//{
|
||||||
this->database->unload();
|
//this->database->unload();
|
||||||
delete this->database;
|
//delete this->database;
|
||||||
}
|
//}
|
||||||
|
|
||||||
this->database = new Database(_db_name);
|
//this->database = new Database(_db_name);
|
||||||
bool flag = this->database->insert(_rdf_path);
|
//bool flag = this->database->insert(_rdf_path);
|
||||||
|
|
||||||
if (flag)
|
//if (flag)
|
||||||
{
|
//{
|
||||||
_ret_msg = "insert triple file to database done.";
|
//_ret_msg = "insert triple file to database done.";
|
||||||
}
|
//}
|
||||||
else
|
//else
|
||||||
{
|
//{
|
||||||
_ret_msg = "import triple file to database failed.";
|
//_ret_msg = "import triple file to database failed.";
|
||||||
}
|
//}
|
||||||
|
|
||||||
return flag;
|
//return flag;
|
||||||
}
|
//}
|
||||||
|
|
||||||
bool
|
bool
|
||||||
Server::query(const string _query, string& _ret_msg)
|
Server::query(const string _query, string& _ret_msg)
|
||||||
|
@ -452,25 +460,47 @@ Server::query(const string _query, string& _ret_msg)
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
FILE* output = stdout;
|
FILE* output = NULL;
|
||||||
string path = "logs/gserver_query.log";
|
string path = "logs/gserver_query.log";
|
||||||
|
#ifdef OUTPUT_QUERY_RESULT
|
||||||
output = fopen(path.c_str(), "w");
|
output = fopen(path.c_str(), "w");
|
||||||
|
#endif
|
||||||
|
|
||||||
ResultSet res_set;
|
ResultSet res_set;
|
||||||
bool flag = this->database->query(_query, res_set, output);
|
int query_ret = this->database->query(_query, res_set, output);
|
||||||
if (output != stdout) {
|
if (output != NULL)
|
||||||
|
{
|
||||||
fclose(output);
|
fclose(output);
|
||||||
output = stdout;
|
|
||||||
}
|
}
|
||||||
if (flag)
|
|
||||||
|
bool flag = true;
|
||||||
|
//cout<<"Server query ret: "<<query_ret<<endl;
|
||||||
|
if (query_ret <= -100) //select query
|
||||||
{
|
{
|
||||||
//_ret_msg = "results are too large!";
|
//_ret_msg = "results are too large!";
|
||||||
//BETTER: divide and transfer if too large to be placed in memory, using Stream
|
//BETTER: divide and transfer if too large to be placed in memory, using Stream
|
||||||
_ret_msg = res_set.to_str();
|
if(query_ret == -100)
|
||||||
|
{
|
||||||
|
_ret_msg = res_set.to_str();
|
||||||
|
}
|
||||||
|
else //query error
|
||||||
|
{
|
||||||
|
flag = false;
|
||||||
|
_ret_msg = "query failed.";
|
||||||
|
//BETTER: {type:select} {success:false}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
else
|
else //update query
|
||||||
{
|
{
|
||||||
_ret_msg = "query failed.";
|
if(query_ret >= 0)
|
||||||
|
{
|
||||||
|
_ret_msg = "update num: " + Util::int2string(query_ret);
|
||||||
|
}
|
||||||
|
else //update error
|
||||||
|
{
|
||||||
|
flag = false;
|
||||||
|
_ret_msg = "update failed.";
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return flag;
|
return flag;
|
||||||
|
|
|
@ -48,7 +48,7 @@ public:
|
||||||
bool unloadDatabase(std::string _db_name, std::string _ac_name, std::string& _ret_msg);
|
bool unloadDatabase(std::string _db_name, std::string _ac_name, std::string& _ret_msg);
|
||||||
bool showDatabases(std::string _para, std::string _ac_name, std::string& _ret_msg);
|
bool showDatabases(std::string _para, std::string _ac_name, std::string& _ret_msg);
|
||||||
bool importRDF(std::string _db_name, std::string _ac_name, std::string _rdf_path, std::string& _ret_msg);
|
bool importRDF(std::string _db_name, std::string _ac_name, std::string _rdf_path, std::string& _ret_msg);
|
||||||
bool insertTriple(std::string _db_name, std::string _ac_name, std::string _rdf_path, std::string& _ret_msg);
|
//bool insertTriple(std::string _db_name, std::string _ac_name, std::string _rdf_path, std::string& _ret_msg);
|
||||||
bool query(const std::string _query, std::string& _ret_msg);
|
bool query(const std::string _query, std::string& _ret_msg);
|
||||||
bool stopServer(std::string& _ret_msg);
|
bool stopServer(std::string& _ret_msg);
|
||||||
|
|
||||||
|
|
|
@ -247,7 +247,7 @@ Util::Util()
|
||||||
this->debug_kvstore = fopen(s.c_str(), "w+");
|
this->debug_kvstore = fopen(s.c_str(), "w+");
|
||||||
if(this->debug_kvstore == NULL)
|
if(this->debug_kvstore == NULL)
|
||||||
{
|
{
|
||||||
printf("open error: kv.log\n");
|
cerr << "open error: kv.log\n";
|
||||||
this->debug_kvstore = stderr;
|
this->debug_kvstore = stderr;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -259,7 +259,7 @@ Util::Util()
|
||||||
this->debug_database = fopen(s.c_str(), "w+");
|
this->debug_database = fopen(s.c_str(), "w+");
|
||||||
if(this->debug_database == NULL)
|
if(this->debug_database == NULL)
|
||||||
{
|
{
|
||||||
printf("open error: db.log\n");
|
cerr << "open error: db.log\n";
|
||||||
this->debug_database = stderr;
|
this->debug_database = stderr;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -271,7 +271,7 @@ Util::Util()
|
||||||
this->debug_vstree = fopen(s.c_str(), "w+");
|
this->debug_vstree = fopen(s.c_str(), "w+");
|
||||||
if(this->debug_vstree == NULL)
|
if(this->debug_vstree == NULL)
|
||||||
{
|
{
|
||||||
printf("open error: vs.log\n");
|
cerr << "open error: vs.log\n";
|
||||||
this->debug_vstree = stderr;
|
this->debug_vstree = stderr;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -660,7 +660,7 @@ string
|
||||||
Util::getQueryFromFile(const char* _file_path)
|
Util::getQueryFromFile(const char* _file_path)
|
||||||
{
|
{
|
||||||
#ifdef DEBUG_PRECISE
|
#ifdef DEBUG_PRECISE
|
||||||
printf("file to open: %s\n", _file_path);
|
cerr << "file to open: " << _file_path <<endl;
|
||||||
#endif
|
#endif
|
||||||
char buf[10000];
|
char buf[10000];
|
||||||
std::string query_file;
|
std::string query_file;
|
||||||
|
@ -775,7 +775,7 @@ Util::getSystemOutput(string cmd)
|
||||||
//fclose(fp);
|
//fclose(fp);
|
||||||
//}
|
//}
|
||||||
system(cmd.c_str());
|
system(cmd.c_str());
|
||||||
cout<<"ans: "<<ans<<endl;
|
//cerr<<"ans: "<<ans<<endl;
|
||||||
return ans;
|
return ans;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1321,4 +1321,4 @@ Util::node2string(const char* _raw_str) {
|
||||||
_output += _raw_str[i];
|
_output += _raw_str[i];
|
||||||
}
|
}
|
||||||
return _output;
|
return _output;
|
||||||
}
|
}
|
||||||
|
|
|
@ -67,6 +67,8 @@ in the sparql query can point to the same node in data graph)
|
||||||
#include <readline/history.h>
|
#include <readline/history.h>
|
||||||
|
|
||||||
#define STREAM_ON 1
|
#define STREAM_ON 1
|
||||||
|
//when used as C/S, if output query result in the server port: default not(you can see the result in the client)
|
||||||
|
//#define OUTPUT_QUERY_RESULT 1
|
||||||
#define READLINE_ON 1
|
#define READLINE_ON 1
|
||||||
#define MULTI_INDEX 1
|
#define MULTI_INDEX 1
|
||||||
//#define SO2P 1
|
//#define SO2P 1
|
||||||
|
@ -74,12 +76,14 @@ in the sparql query can point to the same node in data graph)
|
||||||
//#define USE_GROUP_DELETE 1
|
//#define USE_GROUP_DELETE 1
|
||||||
|
|
||||||
//indicate that in debug mode
|
//indicate that in debug mode
|
||||||
|
#define DEBUG_JOIN
|
||||||
//#define DEBUG_STREAM
|
//#define DEBUG_STREAM
|
||||||
//#define DEBUG_PRECISE 1 all information
|
//#define DEBUG_PRECISE 1 all information
|
||||||
//#define DEBUG_KVSTORE 1 //in KVstore
|
//#define DEBUG_KVSTORE 1 //in KVstore
|
||||||
//#define DEBUG_VSTREE 1 //in Database
|
#define DEBUG_VSTREE 1 //in Database
|
||||||
//#define DEBUG_DATABASE 1 //in Database
|
//#define DEBUG_DATABASE 1 //in Database
|
||||||
//#define DEBUG_JOIN
|
//
|
||||||
|
//
|
||||||
|
|
||||||
#ifdef DEBUG_PRECISE
|
#ifdef DEBUG_PRECISE
|
||||||
#ifndef DEBUG
|
#ifndef DEBUG
|
||||||
|
|
|
@ -44,14 +44,14 @@ LRUCache::LRUCache(int _capacity)
|
||||||
|
|
||||||
LRUCache::~LRUCache()
|
LRUCache::~LRUCache()
|
||||||
{
|
{
|
||||||
delete[]this->next;
|
delete[] this->next;
|
||||||
delete[]this->prev;
|
delete[] this->prev;
|
||||||
delete[]this->keys;
|
delete[] this->keys;
|
||||||
for (int i = 0; i < this->size; ++i)
|
for (int i = 0; i < this->size; ++i)
|
||||||
{
|
{
|
||||||
delete this->values[i];
|
delete this->values[i];
|
||||||
}
|
}
|
||||||
delete[]this->values;
|
delete[] this->values;
|
||||||
}
|
}
|
||||||
|
|
||||||
//load cache's elements from an exist data file.
|
//load cache's elements from an exist data file.
|
||||||
|
|
|
@ -377,7 +377,7 @@ VSTree::insertEntry(const SigEntry& _entry)
|
||||||
VNode* choosedNodePtr = this->chooseNode(this->getRoot(), _entry);
|
VNode* choosedNodePtr = this->chooseNode(this->getRoot(), _entry);
|
||||||
|
|
||||||
#ifdef DEBUG_VSTREE
|
#ifdef DEBUG_VSTREE
|
||||||
if(_entry.getEntityId() == 2402)
|
if(_entry.getEntityId() == 200)
|
||||||
{
|
{
|
||||||
stringstream _ss;
|
stringstream _ss;
|
||||||
if (choosedNodePtr)
|
if (choosedNodePtr)
|
||||||
|
@ -402,6 +402,9 @@ VSTree::insertEntry(const SigEntry& _entry)
|
||||||
|
|
||||||
if (choosedNodePtr->isFull())
|
if (choosedNodePtr->isFull())
|
||||||
{
|
{
|
||||||
|
#ifdef DEBUG_VSTREE
|
||||||
|
cout<<"split occur"<<endl;
|
||||||
|
#endif
|
||||||
//if the choosed leaf node to insert is full, the node should be split.
|
//if the choosed leaf node to insert is full, the node should be split.
|
||||||
this->split(choosedNodePtr, _entry, NULL);
|
this->split(choosedNodePtr, _entry, NULL);
|
||||||
|
|
||||||
|
@ -433,6 +436,10 @@ VSTree::insertEntry(const SigEntry& _entry)
|
||||||
}
|
}
|
||||||
this->entry_num ++;
|
this->entry_num ++;
|
||||||
|
|
||||||
|
#ifdef DEBUG_VSTREE
|
||||||
|
//cout<<"file line check: "<<this->entityID2FileLineMap[200]<<endl;
|
||||||
|
#endif
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -440,6 +447,7 @@ VSTree::insertEntry(const SigEntry& _entry)
|
||||||
bool
|
bool
|
||||||
VSTree::removeEntry(int _entity_id)
|
VSTree::removeEntry(int _entity_id)
|
||||||
{
|
{
|
||||||
|
//cout<<"file line check: "<<this->entityID2FileLineMap[200]<<endl;
|
||||||
VNode* leafNodePtr = this->getLeafNodeByEntityID(_entity_id);
|
VNode* leafNodePtr = this->getLeafNodeByEntityID(_entity_id);
|
||||||
|
|
||||||
if (leafNodePtr == NULL)
|
if (leafNodePtr == NULL)
|
||||||
|
@ -478,6 +486,9 @@ VSTree::removeEntry(int _entity_id)
|
||||||
leafNodePtr->removeChild(entryIndex);
|
leafNodePtr->removeChild(entryIndex);
|
||||||
leafNodePtr->refreshAncestorSignature(*(this->node_buffer));
|
leafNodePtr->refreshAncestorSignature(*(this->node_buffer));
|
||||||
this->removeNode(leafNodePtr);
|
this->removeNode(leafNodePtr);
|
||||||
|
//DEBUG: already deleted in freeElem
|
||||||
|
//delete leafNodePtr;
|
||||||
|
//leafNodePtr = NULL;
|
||||||
this->root_file_line = -1;
|
this->root_file_line = -1;
|
||||||
this->height = 0;
|
this->height = 0;
|
||||||
this->entry_num = 0;
|
this->entry_num = 0;
|
||||||
|
@ -485,6 +496,7 @@ VSTree::removeEntry(int _entity_id)
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
|
//cout<<"root remove a child"<<endl;
|
||||||
leafNodePtr->removeChild(entryIndex);
|
leafNodePtr->removeChild(entryIndex);
|
||||||
leafNodePtr->refreshAncestorSignature(*(this->node_buffer));
|
leafNodePtr->refreshAncestorSignature(*(this->node_buffer));
|
||||||
}
|
}
|
||||||
|
@ -718,57 +730,86 @@ VSTree::split(VNode* _p_node_being_split, const SigEntry& _insert_entry, VNode*
|
||||||
entryIndex_nearB.clear();
|
entryIndex_nearB.clear();
|
||||||
entryIndex_nearA.push_back(entryA_index);
|
entryIndex_nearA.push_back(entryA_index);
|
||||||
entryIndex_nearB.push_back(entryB_index);
|
entryIndex_nearB.push_back(entryB_index);
|
||||||
|
int cnt = 1, i;
|
||||||
|
//BETTER:maybe sort and add?(how to sort according to two seeds)
|
||||||
|
for(i = 0; i < VNode::MAX_CHILD_NUM; ++i)
|
||||||
|
{
|
||||||
|
if(i == entryA_index || i == entryB_index)
|
||||||
|
{
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
if(cnt > VNode::MIN_CHILD_NUM) //num+1
|
||||||
|
{
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
cnt++;
|
||||||
|
entryIndex_nearA.push_back(i);
|
||||||
|
}
|
||||||
|
for(; i < VNode::MAX_CHILD_NUM; ++i)
|
||||||
|
{
|
||||||
|
if(i == entryA_index || i == entryB_index)
|
||||||
|
{
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
entryIndex_nearB.push_back(i);
|
||||||
|
}
|
||||||
|
|
||||||
int nearA_max_size, nearB_max_size;
|
//NOTICE: code below maybe exist error, can not divide evenly(and maybe not necessary to compute distance)
|
||||||
bool nearA_tooSmall, nearB_tooSmall;
|
//
|
||||||
|
//int nearA_max_size, nearB_max_size;
|
||||||
|
//bool nearA_tooSmall, nearB_tooSmall;
|
||||||
|
//for(int i = 0; i < VNode::MAX_CHILD_NUM; i++)
|
||||||
|
//{
|
||||||
|
//if(i == entryA_index || i == entryB_index) continue;
|
||||||
|
|
||||||
for(int i = 0; i < VNode::MAX_CHILD_NUM; i++)
|
////should guarantee that each new node has at least MIN_CHILD_NUM children.
|
||||||
{
|
//nearA_max_size = VNode::MAX_CHILD_NUM - entryIndex_nearB.size();
|
||||||
if(i == entryA_index || i == entryB_index) continue;
|
//nearA_tooSmall = (nearA_max_size < VNode::MIN_CHILD_NUM);
|
||||||
|
|
||||||
//should guarantee that each new node has at least MIN_CHILD_NUM children.
|
////BETTER:is this too wasteful?
|
||||||
nearA_max_size = VNode::MAX_CHILD_NUM - entryIndex_nearB.size();
|
//if(nearA_tooSmall)
|
||||||
nearA_tooSmall = (nearA_max_size <= VNode::MIN_CHILD_NUM);
|
//{
|
||||||
|
//for(; i < VNode::MAX_CHILD_NUM; i++)
|
||||||
|
//{
|
||||||
|
//if (i == entryA_index || i == entryB_index) continue;
|
||||||
|
//entryIndex_nearA.push_back(i);
|
||||||
|
//}
|
||||||
|
//break;
|
||||||
|
//}
|
||||||
|
|
||||||
if(nearA_tooSmall)
|
//nearB_max_size = VNode::MAX_CHILD_NUM - entryIndex_nearA.size();
|
||||||
{
|
//nearB_tooSmall = (nearB_max_size < VNode::MIN_CHILD_NUM);
|
||||||
for(; i < VNode::MAX_CHILD_NUM; i++)
|
//if(nearB_tooSmall)
|
||||||
{
|
//{
|
||||||
if (i == entryA_index || i == entryB_index) continue;
|
//for(; i < VNode::MAX_CHILD_NUM; i++)
|
||||||
entryIndex_nearA.push_back(i);
|
//{
|
||||||
}
|
//if(i == entryA_index || i == entryB_index) continue;
|
||||||
break;
|
//entryIndex_nearB.push_back(i);
|
||||||
}
|
//}
|
||||||
|
//break;
|
||||||
|
//}
|
||||||
|
|
||||||
nearB_max_size = VNode::MAX_CHILD_NUM - entryIndex_nearA.size();
|
////calculate the distance from
|
||||||
nearB_tooSmall = (nearB_max_size <= VNode::MIN_CHILD_NUM);
|
////the i-th child entry signature to seedA(or seedB).
|
||||||
if(nearB_tooSmall)
|
|
||||||
{
|
|
||||||
for(; i < VNode::MAX_CHILD_NUM; i++)
|
|
||||||
{
|
|
||||||
if(i == entryA_index || i == entryB_index) continue;
|
|
||||||
entryIndex_nearB.push_back(i);
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
//calculate the distance from
|
////NOTICE:we should expect that the candidate can be almost contained!
|
||||||
//the i-th child entry signature to seedA(or seedB).
|
////However, the precondition there are not too many 1s
|
||||||
|
//int disToSeedA = entryA.xEpsilen(_p_node_being_split->getChildEntry(i));
|
||||||
|
//int disToSeedB = entryB.xEpsilen(_p_node_being_split->getChildEntry(i));
|
||||||
|
//// choose the near one seed to add into
|
||||||
|
//if(disToSeedA <= disToSeedB)
|
||||||
|
//{
|
||||||
|
//entryIndex_nearA.push_back(i);
|
||||||
|
//}
|
||||||
|
//else
|
||||||
|
//{
|
||||||
|
//entryIndex_nearB.push_back(i);
|
||||||
|
//}
|
||||||
|
//}
|
||||||
|
|
||||||
//NOTICE:we should expect that the candidate can be almost contained!
|
#ifdef DEBUG_VSTREE
|
||||||
//However, the precondition there are not too many 1s
|
cout<<"A: "<<entryIndex_nearA.size()<<" B: "<<entryIndex_nearB.size()<<endl;
|
||||||
int disToSeedA = entryA.xEpsilen(_p_node_being_split->getChildEntry(i));
|
#endif
|
||||||
int disToSeedB = entryB.xEpsilen(_p_node_being_split->getChildEntry(i));
|
|
||||||
// choose the near one seed to add into
|
|
||||||
if(disToSeedA <= disToSeedB)
|
|
||||||
{
|
|
||||||
entryIndex_nearA.push_back(i);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
entryIndex_nearB.push_back(i);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// then create a new node to act as BEntryIndex's father.
|
// then create a new node to act as BEntryIndex's father.
|
||||||
VNode* newNodePtr = this->createNode();
|
VNode* newNodePtr = this->createNode();
|
||||||
|
@ -795,7 +836,6 @@ VSTree::split(VNode* _p_node_being_split, const SigEntry& _insert_entry, VNode*
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
//debug target 2
|
|
||||||
VNode* childPtr = oldNodePtr->getChild(entryIndex_nearB[i], *(this->node_buffer));
|
VNode* childPtr = oldNodePtr->getChild(entryIndex_nearB[i], *(this->node_buffer));
|
||||||
newNodePtr->addChildNode(childPtr);
|
newNodePtr->addChildNode(childPtr);
|
||||||
}
|
}
|
||||||
|
@ -869,8 +909,10 @@ VSTree::split(VNode* _p_node_being_split, const SigEntry& _insert_entry, VNode*
|
||||||
//should keep the root node always being
|
//should keep the root node always being
|
||||||
//at the first line(line zero) of the tree node file.
|
//at the first line(line zero) of the tree node file.
|
||||||
this->swapNodeFileLine(RootNewPtr, oldNodePtr);
|
this->swapNodeFileLine(RootNewPtr, oldNodePtr);
|
||||||
|
cout<<"new root: "<<RootNewPtr->getFileLine()<<endl;
|
||||||
this->height++;
|
this->height++;
|
||||||
this->root_file_line = RootNewPtr->getFileLine();
|
//NOTICE:below is unnecessary
|
||||||
|
//this->root_file_line = RootNewPtr->getFileLine();
|
||||||
|
|
||||||
#ifdef DEBUG
|
#ifdef DEBUG
|
||||||
cout<<"root file line "<<this->root_file_line<<" child num "<<RootNewPtr->getChildNum()<<endl;
|
cout<<"root file line "<<this->root_file_line<<" child num "<<RootNewPtr->getChildNum()<<endl;
|
||||||
|
@ -939,6 +981,7 @@ VSTree::coalesce(VNode* _child, int _entry_index)
|
||||||
|
|
||||||
if(_father == NULL) //this is already root
|
if(_father == NULL) //this is already root
|
||||||
{
|
{
|
||||||
|
//cout<<"the father is NULL!!!"<<endl;
|
||||||
//NOTICE:when root is leaf, at least one key, otherwise the tree is empty
|
//NOTICE:when root is leaf, at least one key, otherwise the tree is empty
|
||||||
//But when root is internal, at least two key, if one key then shrink
|
//But when root is internal, at least two key, if one key then shrink
|
||||||
//(1-key internal root is not permitted)
|
//(1-key internal root is not permitted)
|
||||||
|
@ -951,18 +994,23 @@ VSTree::coalesce(VNode* _child, int _entry_index)
|
||||||
//only one key after remove, shrink root
|
//only one key after remove, shrink root
|
||||||
VNode* newRoot = _child->getChild(0, *(this->node_buffer));
|
VNode* newRoot = _child->getChild(0, *(this->node_buffer));
|
||||||
newRoot->setAsRoot(true);
|
newRoot->setAsRoot(true);
|
||||||
|
#ifdef DEBUG
|
||||||
cout<<"shrink root in coalesce() -- to swap node file"<<endl;
|
cout<<"shrink root in coalesce() -- to swap node file"<<endl;
|
||||||
|
#endif
|
||||||
this->swapNodeFileLine(newRoot, _child);
|
this->swapNodeFileLine(newRoot, _child);
|
||||||
this->root_file_line = newRoot->getFileLine();
|
//this->root_file_line = newRoot->getFileLine();
|
||||||
this->height--;
|
this->height--;
|
||||||
this->removeNode(_child);
|
this->removeNode(_child);
|
||||||
}
|
}
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
//cout<<"num: "<<cn<<endl;
|
||||||
if(cn > VNode::MIN_CHILD_NUM)
|
if(cn > VNode::MIN_CHILD_NUM)
|
||||||
{
|
{
|
||||||
|
#ifdef DEBUG_VSTREE
|
||||||
cout<<"no need to move or union in coalesce()"<<endl;
|
cout<<"no need to move or union in coalesce()"<<endl;
|
||||||
|
#endif
|
||||||
_child->removeChild(_entry_index);
|
_child->removeChild(_entry_index);
|
||||||
_child->refreshAncestorSignature(*(this->node_buffer));
|
_child->refreshAncestorSignature(*(this->node_buffer));
|
||||||
return;
|
return;
|
||||||
|
@ -1158,6 +1206,12 @@ VSTree::coalesce(VNode* _child, int _entry_index)
|
||||||
{
|
{
|
||||||
this->updateEntityID2FileLineMap(p);
|
this->updateEntityID2FileLineMap(p);
|
||||||
}
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
//DEBUG
|
||||||
|
//delete p;
|
||||||
|
//p = NULL;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1356,10 +1410,12 @@ VSTree::loadTreeInfo()
|
||||||
fread(&key, sizeof(int), 1, filePtr);
|
fread(&key, sizeof(int), 1, filePtr);
|
||||||
while(!feof(filePtr))
|
while(!feof(filePtr))
|
||||||
{
|
{
|
||||||
//if(key == 25)
|
#ifdef DEBUG_VSTREE
|
||||||
//{
|
if(key == 1)
|
||||||
//cout<<"loadTreeInfo() - get id 25"<<endl;
|
{
|
||||||
//}
|
cout<<"loadTreeInfo() - get id 1"<<endl;
|
||||||
|
}
|
||||||
|
#endif
|
||||||
this->free_nid_list.push_back(key);
|
this->free_nid_list.push_back(key);
|
||||||
fread(&key, sizeof(int), 1, filePtr);
|
fread(&key, sizeof(int), 1, filePtr);
|
||||||
}
|
}
|
||||||
|
@ -1608,6 +1664,7 @@ VSTree::removeNode(VNode* _vp)
|
||||||
this->node_buffer->del(key);
|
this->node_buffer->del(key);
|
||||||
this->node_num--;
|
this->node_num--;
|
||||||
//delete _vp;
|
//delete _vp;
|
||||||
|
//_vp->setFileLine(-1);
|
||||||
}
|
}
|
||||||
|
|
||||||
string
|
string
|
||||||
|
|
|
@ -1,8 +1,11 @@
|
||||||
|
#CC=g++
|
||||||
|
CC=ccache g++
|
||||||
|
|
||||||
example: CppAPIExample.o
|
example: CppAPIExample.o
|
||||||
g++ -o example CppAPIExample.o -L../lib -lgstoreconnector
|
$(CC) -o example CppAPIExample.o -L../lib -lgstoreconnector
|
||||||
|
|
||||||
CppAPIExample.o: CppAPIExample.cpp
|
CppAPIExample.o: CppAPIExample.cpp
|
||||||
g++ -c -I../src/ CppAPIExample.cpp -o CppAPIExample.o
|
$(CC) -c -I../src/ CppAPIExample.cpp -o CppAPIExample.o
|
||||||
|
|
||||||
clean:
|
clean:
|
||||||
rm -rf *.o example
|
rm -rf *.o example
|
||||||
|
|
|
@ -1,3 +1,6 @@
|
||||||
|
#CC=g++
|
||||||
|
CC=ccache g++
|
||||||
|
|
||||||
lib_dir=../lib/
|
lib_dir=../lib/
|
||||||
socket_obj_dir=../../../.objs/
|
socket_obj_dir=../../../.objs/
|
||||||
|
|
||||||
|
@ -7,7 +10,7 @@ $(lib_dir)libgstoreconnector.a: GstoreConnector.o $(socket_obj_dir)Socket.o
|
||||||
ar -crv $(lib_dir)libgstoreconnector.a GstoreConnector.o $(socket_obj_dir)Socket.o
|
ar -crv $(lib_dir)libgstoreconnector.a GstoreConnector.o $(socket_obj_dir)Socket.o
|
||||||
|
|
||||||
GstoreConnector.o: GstoreConnector.cpp GstoreConnector.h $(socket_obj_dir)Socket.o
|
GstoreConnector.o: GstoreConnector.cpp GstoreConnector.h $(socket_obj_dir)Socket.o
|
||||||
g++ -c GstoreConnector.cpp -o GstoreConnector.o
|
$(CC) -c GstoreConnector.cpp -o GstoreConnector.o
|
||||||
|
|
||||||
clean:
|
clean:
|
||||||
rm -rf GstoreConnector.o $(lib_dir)libgstoreconnector.a
|
rm -rf GstoreConnector.o $(lib_dir)libgstoreconnector.a
|
||||||
|
|
|
@ -1,4 +1,4 @@
|
||||||
select ?s ?p ?o where
|
select ?s ?o where
|
||||||
{
|
{
|
||||||
?s ?p ?o .
|
?s ?p ?o .
|
||||||
}
|
}
|
||||||
|
|
|
@ -0,0 +1,4 @@
|
||||||
|
select ?x ?p where
|
||||||
|
{
|
||||||
|
?x ?p <FullProfessor0>.
|
||||||
|
}
|
|
@ -0,0 +1,9 @@
|
||||||
|
select distinct ?x ?p1 ?p2 where
|
||||||
|
{
|
||||||
|
?x <rdf:type> <ub:GraduateStudent>.
|
||||||
|
?y <rdf:type> <ub:University>.
|
||||||
|
?z <rdf:type> <ub:Department>.
|
||||||
|
?x ?p1 ?z.
|
||||||
|
?z ?p2 ?y.
|
||||||
|
?x <ub:undergraduateDegreeFrom> ?y.
|
||||||
|
}
|
|
@ -0,0 +1,10 @@
|
||||||
|
select distinct ?x ?p1 ?p2 ?p3 where
|
||||||
|
{
|
||||||
|
?x <rdf:type> <ub:UndergraduateStudent>.
|
||||||
|
?y <ub:name> <Course1>.
|
||||||
|
?x ?p1 ?y.
|
||||||
|
?z <ub:teacherOf> ?y.
|
||||||
|
?z <ub:name> <FullProfessor1>.
|
||||||
|
?z ?p2 ?w.
|
||||||
|
?w ?p3 <Department0>.
|
||||||
|
}
|
|
@ -0,0 +1,4 @@
|
||||||
|
select distinct ?x where
|
||||||
|
{
|
||||||
|
?x <rdf:type> <ub:UndergraduateStudent>.
|
||||||
|
}
|
|
@ -0,0 +1,4 @@
|
||||||
|
select ?p where
|
||||||
|
{
|
||||||
|
<s0> ?p <o0> .
|
||||||
|
}
|
|
@ -0,0 +1,5 @@
|
||||||
|
select ?s ?o where
|
||||||
|
{
|
||||||
|
?s <p0> ?o .
|
||||||
|
?s <p1> ?o .
|
||||||
|
}
|
|
@ -0,0 +1,5 @@
|
||||||
|
select ?s ?p ?o ?p2 ?o2 where
|
||||||
|
{
|
||||||
|
?s ?p ?o .
|
||||||
|
?o ?p2 ?o2 .
|
||||||
|
}
|
|
@ -0,0 +1,5 @@
|
||||||
|
select ?s ?p2 ?o2 where
|
||||||
|
{
|
||||||
|
?s ?p ?o .
|
||||||
|
?o ?p2 ?o2 .
|
||||||
|
}
|
|
@ -0,0 +1,6 @@
|
||||||
|
select ?s1 ?s2 ?p3 ?o where
|
||||||
|
{
|
||||||
|
?s1 ?p1 ?o .
|
||||||
|
?s2 ?p2 ?o .
|
||||||
|
?s3 ?p3 ?o .
|
||||||
|
}
|
|
@ -0,0 +1,7 @@
|
||||||
|
select ?s1 ?s2 ?p3 ?o where
|
||||||
|
{
|
||||||
|
?s1 ?p1 ?o .
|
||||||
|
?s2 ?p2 ?o .
|
||||||
|
?s3 ?p3 ?o .
|
||||||
|
?s1 ?p4 ?o2 .
|
||||||
|
}
|
|
@ -1,4 +0,0 @@
|
||||||
select ?s ?o where
|
|
||||||
{
|
|
||||||
?s ?p ?o .
|
|
||||||
}
|
|
|
@ -0,0 +1,6 @@
|
||||||
|
select ?v2 ?v0 where
|
||||||
|
{
|
||||||
|
?v0 <own> ?v1 .
|
||||||
|
?v0 <own> ?v2 .
|
||||||
|
?v1 <close> ?v2 .
|
||||||
|
}
|
|
@ -15,6 +15,7 @@ readline-devel | need to be installed
|
||||||
openjdk | needed if using Java api
|
openjdk | needed if using Java api
|
||||||
openjdk-devel | needed if using Java api
|
openjdk-devel | needed if using Java api
|
||||||
realpath | needed if using gconsole
|
realpath | needed if using gconsole
|
||||||
|
ccache | optional, used to speed up the compilation
|
||||||
|
|
||||||
NOTICE:
|
NOTICE:
|
||||||
|
|
||||||
|
@ -22,13 +23,15 @@ NOTICE:
|
||||||
|
|
||||||
2. To install readline and readline-devel, just type `dnf install readline-devel` in Redhat/CentOS/Fedora, or `apt-get install libreadline-dev` in Debian/Ubuntu. Please use corresponding commands in other systems. If you use ArchLinux, just type `pacman -S readline` to install the readline and readline-devel.(so do other packages)
|
2. To install readline and readline-devel, just type `dnf install readline-devel` in Redhat/CentOS/Fedora, or `apt-get install libreadline-dev` in Debian/Ubuntu. Please use corresponding commands in other systems. If you use ArchLinux, just type `pacman -S readline` to install the readline and readline-devel.(so do other packages)
|
||||||
|
|
||||||
3. You do not have to install realpath to use gStore, but if you want to use the gconsole for its convenience, please do so by using `dnf install realpath` or `apt-get install realpath`.
|
3. You do not have to install realpath to use gStore, but if you want to use the gconsole for its convenience, please do so by using `dnf install realpath` or `apt-get install realpath`. However, if you can not install realpath in your system, please go to modify the file Main/gconsole.cpp(just find the place using realpath command and remove the realpath command).
|
||||||
|
|
||||||
4. Our programs use regEx functions, which are provided by GNU/Linux by default. You do not need to have to install boost and boost-devel for more powerful regEx libraries.
|
4. Our programs use regEx functions, which are provided by GNU/Linux by default. You do not need to install boost and boost-devel for more powerful regEx libraries.
|
||||||
|
|
||||||
5. ANTLR3.4 is used in gStore to produce lexer and parser code for SPARQL query. However, you do not need to install the corresponding antlr libraries because we have merged the libantlr3.4 in our system.
|
5. ANTLR3.4 is used in gStore to produce lexer and parser code for SPARQL query. However, you do not need to install the corresponding antlr libraries because we have merged the libantlr3.4 in our system.
|
||||||
|
|
||||||
6. When you type `make` in the root directory of the gStore project, the Java api will also be compiled. You can modify the makefile if you do not have JDK in your system. However, you are advised to install openjdk-devel in your Linux system.
|
6. When you type `make` in the root directory of the gStore project, the Java api will also be compiled. You can modify the makefile if you do not have JDK in your system. However, you are advised to install openjdk-devel in your Linux system.
|
||||||
|
|
||||||
7. Any other questions, please go to [FAQ](FAQ.md) page.
|
7. To install ccache, you need to add epel repository if using CentOS, while in Ubuntu you can directly install it by `apt-get install ccache` command. If you can not install ccache(or maybe you do not want to), please go to modify the makefile(just change the CC variable to g++).
|
||||||
|
|
||||||
|
8. Any other questions, please go to [FAQ](FAQ.md) page.
|
||||||
|
|
||||||
|
|
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
|
@ -253,6 +253,7 @@ readline-devel & need to be installed\tabularnewline
|
||||||
openjdk & needed if using Java api\tabularnewline
|
openjdk & needed if using Java api\tabularnewline
|
||||||
openjdk-devel & needed if using Java api\tabularnewline
|
openjdk-devel & needed if using Java api\tabularnewline
|
||||||
realpath & needed if using gconsole\tabularnewline
|
realpath & needed if using gconsole\tabularnewline
|
||||||
|
ccache & optional, used to speed up the compilation\tabularnewline
|
||||||
\bottomrule
|
\bottomrule
|
||||||
\caption{software requirement}
|
\caption{software requirement}
|
||||||
\end{longtable}
|
\end{longtable}
|
||||||
|
@ -265,13 +266,15 @@ NOTICE:
|
||||||
\item
|
\item
|
||||||
To install readline and readline-devel, just type \texttt{dnf\ install\ readline-devel} in Redhat/CentOS/Fedora, or \texttt{apt-get\ install\ libreadline-dev} in Debian/Ubuntu. Please use corresponding commands in other systems. If you use ArchLinux, just type \texttt{pacman\ -S\ readline} to install the readline and readline-devel.(so do other packages)
|
To install readline and readline-devel, just type \texttt{dnf\ install\ readline-devel} in Redhat/CentOS/Fedora, or \texttt{apt-get\ install\ libreadline-dev} in Debian/Ubuntu. Please use corresponding commands in other systems. If you use ArchLinux, just type \texttt{pacman\ -S\ readline} to install the readline and readline-devel.(so do other packages)
|
||||||
\item
|
\item
|
||||||
You do not have to install realpath to use gStore, but if you want to use the gconsole for its convenience, please do so by using \texttt{dnf\ install\ realpath} or \texttt{apt-get\ install\ realpath}.
|
You do not have to install realpath to use gStore, but if you want to use the gconsole for its convenience, please do so by using \texttt{dnf\ install\ realpath} or \texttt{apt-get\ install\ realpath}. However, if you can not install realpath in your system, please go to modify the file Main/gconsole.cpp(just find the place using realpath command and remove the realpath command).
|
||||||
\item
|
\item
|
||||||
Our programs use regEx functions, which are provided by GNU/Linux by default. You do not need to have to install boost and boost-devel for more powerful regEx libraries.
|
Our programs use regEx functions, which are provided by GNU/Linux by default. You do not need to install boost and boost-devel for more powerful regEx libraries.
|
||||||
\item
|
\item
|
||||||
ANTLR3.4 is used in gStore to produce lexer and parser code for SPARQL query. However, you do not need to install the corresponding antlr libraries because we have merged the libantlr3.4 in our system.
|
ANTLR3.4 is used in gStore to produce lexer and parser code for SPARQL query. However, you do not need to install the corresponding antlr libraries because we have merged the libantlr3.4 in our system.
|
||||||
\item
|
\item
|
||||||
When you type \texttt{make} in the root directory of the gStore project, the Java api will also be compiled. You can modify the makefile if you do not have JDK in your system. However, you are advised to install openjdk-devel in your Linux system.
|
When you type \texttt{make} in the root directory of the gStore project, the Java api will also be compiled. You can modify the makefile if you do not have JDK in your system. However, you are advised to install openjdk-devel in your Linux system.
|
||||||
|
\item
|
||||||
|
To install ccache, you need to add epel repository if using CentOS, while in Ubuntu you can directly install it by `apt-get install ccache` command. If you can not install ccache(or maybe you do not want to), please go to modify the makefile(just change the CC variable to g++).
|
||||||
\item
|
\item
|
||||||
Any other questions, please go to \hyperref[chapter10]{FAQ} page.
|
Any other questions, please go to \hyperref[chapter10]{FAQ} page.
|
||||||
\end{enumerate}
|
\end{enumerate}
|
||||||
|
|
Binary file not shown.
|
@ -394,6 +394,7 @@ Gstore系统(也称作gStore)是一个用于管理大型图结构数据的
|
||||||
openjdk & 使用Java api时需要 \\
|
openjdk & 使用Java api时需要 \\
|
||||||
openjdk-devel & 使用Java api时需要 \\
|
openjdk-devel & 使用Java api时需要 \\
|
||||||
realpath & 使用gconsole时需要 \\
|
realpath & 使用gconsole时需要 \\
|
||||||
|
ccache & 可选, 可以加速编译过程 \\
|
||||||
\bottomrule
|
\bottomrule
|
||||||
\end{tabular}
|
\end{tabular}
|
||||||
\caption{软件要求}
|
\caption{软件要求}
|
||||||
|
@ -407,7 +408,7 @@ Gstore系统(也称作gStore)是一个用于管理大型图结构数据的
|
||||||
\item
|
\item
|
||||||
要安装readline和readline-devel,只需要在Redhat/CentOS/Fedora中输入\texttt{dnf\ install\ readline-devel},或者在Debian/Ubuntu 中输入\texttt{apt-get\ install\ libreadline-dev}。请在其他系统中使用对应的指令。如果你使用的是ArchLinux,只要输入\texttt{pacman\ -S\ readline}就可以安装readline和readline-devel。(其他包也一样)
|
要安装readline和readline-devel,只需要在Redhat/CentOS/Fedora中输入\texttt{dnf\ install\ readline-devel},或者在Debian/Ubuntu 中输入\texttt{apt-get\ install\ libreadline-dev}。请在其他系统中使用对应的指令。如果你使用的是ArchLinux,只要输入\texttt{pacman\ -S\ readline}就可以安装readline和readline-devel。(其他包也一样)
|
||||||
\item
|
\item
|
||||||
使用gStore不需要安装realpath,但如果你想要使用gconsole,请输入\texttt{dnf\ install\ realpath}或\texttt{apt-get\ install\ realpath}进行安装。
|
使用gStore不需要安装realpath,但如果你想要使用gconsole,请输入\texttt{dnf\ install\ realpath}或\texttt{apt-get\ install\ realpath}进行安装。 然而,如果你不想安装realpath,请修改Main/gconsole.cpp文件(找到使用realpath的地方并移除realpath命令即可)。
|
||||||
\item
|
\item
|
||||||
我们的项目使用了正则表达式,由GNU/Linux默认提供。要使用更强大的正则表达式库,你不需要安装boost和boost-devel。
|
我们的项目使用了正则表达式,由GNU/Linux默认提供。要使用更强大的正则表达式库,你不需要安装boost和boost-devel。
|
||||||
\item
|
\item
|
||||||
|
@ -415,6 +416,8 @@ Gstore系统(也称作gStore)是一个用于管理大型图结构数据的
|
||||||
\item
|
\item
|
||||||
当你在gStore项目的根目录下输入\texttt{make}时,Java api也会编译。如果你的系统里没有JDK,你可以修改makefile。我们建议你在Linux系统中安装openjdk-devel。
|
当你在gStore项目的根目录下输入\texttt{make}时,Java api也会编译。如果你的系统里没有JDK,你可以修改makefile。我们建议你在Linux系统中安装openjdk-devel。
|
||||||
\item
|
\item
|
||||||
|
在CentOS系统上你需要添加epel源才能安装ccache,但在Ubuntu系统上你可以直接安装。如果你无法安装ccache(或者你不想安装),请修改makefile文件(只需将CC变量改为g++即可)。
|
||||||
|
\item
|
||||||
其他问题请参阅\hyperref[chapter10]{【FAQ】}一章。
|
其他问题请参阅\hyperref[chapter10]{【FAQ】}一章。
|
||||||
\end{enumerate}
|
\end{enumerate}
|
||||||
|
|
||||||
|
|
|
@ -18,22 +18,29 @@
|
||||||
#(also include good comments norm)
|
#(also include good comments norm)
|
||||||
#http://blog.csdn.net/u010740725/article/details/51387810
|
#http://blog.csdn.net/u010740725/article/details/51387810
|
||||||
|
|
||||||
|
#NOTICE: to speed up the make process, use make -j4
|
||||||
|
#use -j8 or higher may cause error
|
||||||
|
#http://blog.csdn.net/cscrazybing/article/details/50789482
|
||||||
|
#http://blog.163.com/liuhonggaono1@126/blog/static/10497901201210254622141/
|
||||||
|
|
||||||
|
|
||||||
#TODO:the dependences are not complete!
|
#TODO:the dependences are not complete!
|
||||||
|
|
||||||
#compile parameters
|
#compile parameters
|
||||||
|
|
||||||
CC = g++
|
CC = ccache g++
|
||||||
|
#CC = g++
|
||||||
|
|
||||||
#the optimazition level of gcc/g++
|
#the optimazition level of gcc/g++
|
||||||
#http://blog.csdn.net/hit_090420216/article/details/44900215
|
#http://blog.csdn.net/hit_090420216/article/details/44900215
|
||||||
#NOTICE: -O2 is recommended, while -O3 is dangerous
|
#NOTICE: -O2 is recommended, while -O3 is dangerous
|
||||||
#when developing, not use -O because it will disturb the normal
|
#when developing, not use -O because it will disturb the normal
|
||||||
#routine. use it for test and release.
|
#routine. use it for test and release.
|
||||||
#CFLAGS = -c -Wall -g #-fprofile-arcs -ftest-coverage #-pg
|
CFLAGS = -c -Wall -g #-fprofile-arcs -ftest-coverage #-pg
|
||||||
#EXEFLAG = -g #-fprofile-arcs -ftest-coverage #-pg
|
EXEFLAG = -g #-fprofile-arcs -ftest-coverage #-pg
|
||||||
#-coverage
|
#-coverage
|
||||||
CFLAGS = -c -Wall -O2
|
#CFLAGS = -c -Wall -O2
|
||||||
EXEFLAG = -O2
|
#EXEFLAG = -O2
|
||||||
|
|
||||||
#add -lreadline -ltermcap if using readline or objs contain readline
|
#add -lreadline -ltermcap if using readline or objs contain readline
|
||||||
library = -ltermcap -lreadline -L./lib -lantlr -lgcov
|
library = -ltermcap -lreadline -L./lib -lantlr -lgcov
|
||||||
|
@ -84,12 +91,21 @@ objfile = $(kvstoreobj) $(vstreeobj) $(stringindexobj) $(parserobj) $(serverobj)
|
||||||
inc = -I./tools/libantlr3c-3.4/ -I./tools/libantlr3c-3.4/include
|
inc = -I./tools/libantlr3c-3.4/ -I./tools/libantlr3c-3.4/include
|
||||||
|
|
||||||
|
|
||||||
|
#auto generate dependencies
|
||||||
|
# http://blog.csdn.net/gmpy_tiger/article/details/51849474
|
||||||
|
# http://blog.csdn.net/jeffrey0000/article/details/12421317
|
||||||
|
|
||||||
#gtest
|
#gtest
|
||||||
all: $(exedir)gbuild $(exedir)gserver $(exedir)gclient $(exedir)gquery $(exedir)gconsole $(api_java) $(exedir)gadd $(exedir)gsub
|
TARGET = $(exedir)gbuild $(exedir)gserver $(exedir)gclient $(exedir)gquery $(exedir)gconsole $(api_java) $(exedir)gadd $(exedir)gsub
|
||||||
|
|
||||||
|
all: $(TARGET)
|
||||||
|
|
||||||
test_index: test_index.cpp
|
test_index: test_index.cpp
|
||||||
$(CC) $(EXEFLAG) -o test_index test_index.cpp $(objfile) $(library)
|
$(CC) $(EXEFLAG) -o test_index test_index.cpp $(objfile) $(library)
|
||||||
|
|
||||||
|
#BETTER: use for loop to reduce the lines
|
||||||
|
#NOTICE: g++ -MM will run error if linking failed, like Database.h/../SparlParser.h/../antlr3.h
|
||||||
|
|
||||||
#executables begin
|
#executables begin
|
||||||
|
|
||||||
#NOTICE:not include g*.o in objfile due to multiple definitions of main()
|
#NOTICE:not include g*.o in objfile due to multiple definitions of main()
|
||||||
|
@ -374,10 +390,12 @@ clean:
|
||||||
rm -rf $(exedir)g* $(objdir)*.o $(exedir).gserver*
|
rm -rf $(exedir)g* $(objdir)*.o $(exedir).gserver*
|
||||||
#rm -rf .project .cproject .settings just for eclipse
|
#rm -rf .project .cproject .settings just for eclipse
|
||||||
#rm -rf cscope* just for vim
|
#rm -rf cscope* just for vim
|
||||||
|
rm -rf logs/*.log
|
||||||
|
|
||||||
dist: clean
|
dist: clean
|
||||||
rm -rf *.nt *.n3 .debug/*.log .tmp/*.dat *.txt *.db
|
rm -rf *.nt *.n3 .debug/*.log .tmp/*.dat *.txt *.db
|
||||||
rm -rf tools/libantlr3c-3.4 lib/libantlr.a Parser/Sparql*
|
rm -rf tools/libantlr3c-3.4 lib/libantlr.a Parser/Sparql*
|
||||||
|
#rm -rf Parser/SparqlLexer* Parser/SparlParser.cpp
|
||||||
rm -rf cscope* .cproject .settings tags
|
rm -rf cscope* .cproject .settings tags
|
||||||
rm -rf *.info
|
rm -rf *.info
|
||||||
|
|
||||||
|
|
|
@ -0,0 +1,286 @@
|
||||||
|
#help for make
|
||||||
|
#http://www.cnblogs.com/wang_yb/p/3990952.html
|
||||||
|
#https://segmentfault.com/a/1190000000349917
|
||||||
|
#http://blog.csdn.net/cuiyifang/article/details/7910268
|
||||||
|
|
||||||
|
#to use gprof to analyse efficience of the program:
|
||||||
|
#http://blog.chinaunix.net/uid-25194149-id-3215487.html
|
||||||
|
|
||||||
|
#to use gcov and lcov
|
||||||
|
#Notice that optimization should not be used here
|
||||||
|
#http://blog.163.com/bobile45@126/blog/static/96061992201382025729313/
|
||||||
|
#gcov -a main.cpp
|
||||||
|
#lcov --directory . --capture --output-file dig.info
|
||||||
|
#genhtml --output-directory . --frames --show-details dig.info
|
||||||
|
|
||||||
|
#to use doxygen+graphviz+htmlhelp to generate document from source code:
|
||||||
|
#http://www.ooxygen.nl/
|
||||||
|
#(also include good comments norm)
|
||||||
|
#http://blog.csdn.net/u010740725/article/details/51387810
|
||||||
|
|
||||||
|
#NOTICE: to speed up the make process, use make -j4
|
||||||
|
#use -j8 or higher may cause error
|
||||||
|
#http://blog.csdn.net/cscrazybing/article/details/50789482
|
||||||
|
#http://blog.163.com/liuhonggaono1@126/blog/static/10497901201210254622141/
|
||||||
|
|
||||||
|
|
||||||
|
#TODO:the dependences are not complete!
|
||||||
|
|
||||||
|
#compile parameters
|
||||||
|
|
||||||
|
CC = ccache g++
|
||||||
|
#CC = g++
|
||||||
|
|
||||||
|
#the optimazition level of gcc/g++
|
||||||
|
#http://blog.csdn.net/hit_090420216/article/details/44900215
|
||||||
|
#NOTICE: -O2 is recommended, while -O3 is dangerous
|
||||||
|
#when developing, not use -O because it will disturb the normal
|
||||||
|
#routine. use it for test and release.
|
||||||
|
#CFLAGS = -c -Wall -g #-fprofile-arcs -ftest-coverage #-pg
|
||||||
|
#EXEFLAG = -g #-fprofile-arcs -ftest-coverage #-pg
|
||||||
|
#-coverage
|
||||||
|
CFLAGS = -c -Wall -O2
|
||||||
|
EXEFLAG = -O2
|
||||||
|
|
||||||
|
#add -lreadline -ltermcap if using readline or objs contain readline
|
||||||
|
library = -ltermcap -lreadline -L./lib -lantlr -lgcov
|
||||||
|
def64IO = -D_FILE_OFFSET_BITS=64 -D_LARGEFILE64_SOURCE
|
||||||
|
|
||||||
|
# paths
|
||||||
|
|
||||||
|
objdir = .objs/
|
||||||
|
|
||||||
|
exedir = bin/
|
||||||
|
|
||||||
|
lib_antlr = lib/libantlr.a
|
||||||
|
|
||||||
|
api_cpp = api/cpp/lib/libgstoreconnector.a
|
||||||
|
|
||||||
|
api_java = api/java/lib/GstoreJavaAPI.jar
|
||||||
|
|
||||||
|
|
||||||
|
inc = -I./tools/libantlr3c-3.4/ -I./tools/libantlr3c-3.4/include
|
||||||
|
|
||||||
|
|
||||||
|
#gtest
|
||||||
|
TARGET = $(exedir)gbuild $(exedir)gserver $(exedir)gclient $(exedir)gquery $(exedir)gconsole $(api_java) $(exedir)gadd $(exedir)gsub
|
||||||
|
|
||||||
|
objfile = $(objdir)SPARQLquery.o $(objdir)Database.o $(objdir)DBparser.o $(objdir)SparlParser.o $(objdir)SparqlLexer.o \
|
||||||
|
$(objdir)QueryParser.o $(objdir)Server.o $(objdir)GeneralEvaluation.o
|
||||||
|
|
||||||
|
#auto generate dependencies
|
||||||
|
# http://blog.csdn.net/gmpy_tiger/article/details/51849474
|
||||||
|
# http://blog.csdn.net/jeffrey0000/article/details/12421317
|
||||||
|
|
||||||
|
DEPEND = Util/Util.d Util/Bstr.d Util/Stream.d Util/Stream.d Util/Triple.d Util/BloomFilter.d \
|
||||||
|
KVstore/SITree/SITree.d KVstore/SITree/SIStorage.d KVstore/SITree/SINode.d KVstore/SITree/SIIntlNode.d KVstore/SITree/SILeafNode.d KVstore/SITree/SIHeap.d \
|
||||||
|
KVstore/ISTree/ISTree.d KVstore/ISTree/ISStorage.d KVstore/ISTree/ISNode.d KVstore/ISTree/ISIntlNode.d KVstore/ISTree/ISLeafNode.d KVstore/ISTree/ISHeap.d \
|
||||||
|
KVstore/KVstore.d Query/BasicQuery.d Query/ResultSet.d Query/IDList.d Database/Join.d Database/Strategy.d \
|
||||||
|
Query/Varset.d Query/QueryTree.d Query/ResultFilter.d StringIndex/StringIndex.d \
|
||||||
|
Signature/SigEntry.d Signature/Signature.d VSTree/VSTree.d VSTree/EntryBuffer.d VSTree/LRUCache.d VSTree/VNode.d \
|
||||||
|
Parser/RDFParser.d Parser/TurtleParser.d Server/Operation.d Server/Client.d Server/Socket.d
|
||||||
|
|
||||||
|
|
||||||
|
#NOTICE: not place tab before include
|
||||||
|
#-include Util/Util.d
|
||||||
|
#sinclude?
|
||||||
|
|
||||||
|
all: $(TARGET)
|
||||||
|
-include $(DEPEND)
|
||||||
|
|
||||||
|
test_index: test_index.cpp
|
||||||
|
$(CC) $(EXEFLAG) -o test_index test_index.cpp $(objfile) $(library)
|
||||||
|
|
||||||
|
#executables begin
|
||||||
|
|
||||||
|
#BETTER: use for loop to reduce the lines
|
||||||
|
#NOTICE: g++ -MM will run error if linking failed, like Database.h/../SparlParser.h/../antlr3.h
|
||||||
|
|
||||||
|
#NOTICE:not include g*.o in objfile due to multiple definitions of main()
|
||||||
|
$(exedir)gbuild: $(lib_antlr) $(objdir)gbuild.o $(objfile)
|
||||||
|
$(CC) $(EXEFLAG) -o $(exedir)gbuild $(objdir)gbuild.o $(objfile) $(library)
|
||||||
|
|
||||||
|
$(exedir)gquery: $(lib_antlr) $(objdir)gquery.o $(objfile)
|
||||||
|
$(CC) $(EXEFLAG) -o $(exedir)gquery $(objdir)gquery.o $(objfile) $(library)
|
||||||
|
|
||||||
|
$(exedir)gserver: $(lib_antlr) $(objdir)gserver.o $(objfile)
|
||||||
|
$(CC) $(EXEFLAG) -o $(exedir)gserver $(objdir)gserver.o $(objfile) $(library)
|
||||||
|
|
||||||
|
$(exedir)gclient: $(lib_antlr) $(objdir)gclient.o $(objfile)
|
||||||
|
$(CC) $(EXEFLAG) -o $(exedir)gclient $(objdir)gclient.o $(objfile) $(library)
|
||||||
|
|
||||||
|
$(exedir)gconsole: $(lib_antlr) $(objdir)gconsole.o $(objfile) $(api_cpp)
|
||||||
|
$(CC) $(EXEFLAG) -o $(exedir)gconsole $(objdir)gconsole.o $(objfile) $(library) -L./api/cpp/lib -lgstoreconnector
|
||||||
|
|
||||||
|
#executables end
|
||||||
|
|
||||||
|
|
||||||
|
#objects in Main/ begin
|
||||||
|
|
||||||
|
$(objdir)gbuild.o: Main/gbuild.cpp Database/Database.h Util/Util.h $(lib_antlr)
|
||||||
|
$(CC) $(CFLAGS) Main/gbuild.cpp $(inc) -o $(objdir)gbuild.o
|
||||||
|
|
||||||
|
$(objdir)gquery.o: Main/gquery.cpp Database/Database.h Util/Util.h $(lib_antlr)
|
||||||
|
$(CC) $(CFLAGS) Main/gquery.cpp $(inc) -o $(objdir)gquery.o #-DREADLINE_ON
|
||||||
|
#add -DREADLINE_ON if using readline
|
||||||
|
|
||||||
|
$(objdir)gserver.o: Main/gserver.cpp Server/Server.h Util/Util.h $(lib_antlr)
|
||||||
|
$(CC) $(CFLAGS) Main/gserver.cpp $(inc) -o $(objdir)gserver.o
|
||||||
|
|
||||||
|
$(objdir)gclient.o: Main/gclient.cpp Server/Client.h Util/Util.h $(lib_antlr)
|
||||||
|
$(CC) $(CFLAGS) Main/gclient.cpp $(inc) -o $(objdir)gclient.o #-DREADLINE_ON
|
||||||
|
|
||||||
|
$(objdir)gconsole.o: Main/gconsole.cpp Database/Database.h Util/Util.h api/cpp/src/GstoreConnector.h $(lib_antlr)
|
||||||
|
$(CC) $(CFLAGS) Main/gconsole.cpp $(inc) -o $(objdir)gconsole.o -I./api/cpp/src/ #-DREADLINE_ON
|
||||||
|
|
||||||
|
#objects in Main/ end
|
||||||
|
|
||||||
|
# auto generated objects
|
||||||
|
|
||||||
|
#TODO+DEBUG:
|
||||||
|
#TODO:maybe multiple lines? how about auto compile with given CC/CFLAGS args? \\n
|
||||||
|
%.d: %.cpp
|
||||||
|
$(CC) -MM $^ > $@.tmp2
|
||||||
|
sed "s/\(\\\n\)/ /g" < $@.tmp2 > $@.tmp
|
||||||
|
#sed "s/\([^\.]*\)\(\.o: \)\([^\/]*\)/.objs\/\1.o \3\/\1.d: \3/g" < $@.tmp > $@
|
||||||
|
sed "s/\([^\.]*\)\(\.o: \)\([^\/]*\)\(.*\)/.objs\/\1.o: \3\4\n\t$(CC) $(CFLAGS) \3\/\1.cpp -o .objs\/\1.o/g" < $@.tmp > $@
|
||||||
|
#tmp=$^
|
||||||
|
#dir=${tmp%/*}
|
||||||
|
#tmp2=${tmp#*/}
|
||||||
|
#name=${tmp2%.*}
|
||||||
|
#NOTICE: use "" instead of '' if need to use shell var
|
||||||
|
#sed "s/\(${name}.o\)/$(objdir)\1 $@/g" < $@.tmp > $@
|
||||||
|
rm $@.tmp*
|
||||||
|
|
||||||
|
# special objects
|
||||||
|
|
||||||
|
$(objdir)Database.o: Database/Database.cpp Database/Database.h \
|
||||||
|
Util/Util.h Util/Triple.h Parser/DBparser.h Parser/SparlParser.h Parser/RDFParser.h \
|
||||||
|
Query/IDList.h Query/ResultSet.h Query/SPARQLquery.h Query/BasicQuery.h \
|
||||||
|
Signature/SigEntry.h KVstore/KVstore.h VSTree/VSTree.h
|
||||||
|
$(CC) $(CFLAGS) Database/Database.cpp $(inc) -o $(objdir)Database.o
|
||||||
|
|
||||||
|
$(objdir)DBparser.o: Parser/DBparser.cpp Parser/DBparser.h $(objdir)SparqlParser.o $(objdir)SparqlLexer.o $(objdir)Triple.o $(objdir)SPARQLquery.o
|
||||||
|
$(CC) $(CFLAGS) Parser/DBparser.cpp $(inc) -o $(objdir)DBparser.o
|
||||||
|
|
||||||
|
$(objdir)SparqlParser.o: Parser/SparqlParser.c Parser/SparqlParser.h
|
||||||
|
gcc $(CFLAGS) Parser/SparqlParser.c $(inc) -o $(objdir)SparqlParser.o
|
||||||
|
|
||||||
|
$(objdir)SparqlLexer.o: Parser/SparqlLexer.c Parser/SparqlLexer.h
|
||||||
|
gcc $(CFLAGS) Parser/SparqlLexer.c $(inc) -o $(objdir)SparqlLexer.o
|
||||||
|
|
||||||
|
$(objdir)QueryParser.o: Parser/QueryParser.cpp Parser/QueryParser.h $(objdir)SparqlParser.o $(objdir)SparqlLexer.o $(objdir)QueryTree.o $(objdir)Util.o
|
||||||
|
$(CC) $(CFLAGS) Parser/QueryParser.cpp $(inc) -o $(objdir)QueryParser.o
|
||||||
|
|
||||||
|
$(objdir)Server.o: Server/Server.cpp Server/Server.h $(objdir)Socket.o $(objdir)Database.o $(objdir)Operation.o $(objdir)Util.o
|
||||||
|
$(CC) $(CFLAGS) Server/Server.cpp $(inc) -o $(objdir)Server.o
|
||||||
|
|
||||||
|
$(objdir)SPARQLquery.o: Query/SPARQLquery.cpp Query/SPARQLquery.h $(objdir)BasicQuery.o
|
||||||
|
$(CC) $(CFLAGS) Query/SPARQLquery.cpp $(inc) -o $(objdir)SPARQLquery.o
|
||||||
|
|
||||||
|
$(objdir)GeneralEvaluation.o: Query/GeneralEvaluation.cpp Query/GeneralEvaluation.h $(objdir)QueryParser.o $(objdir)QueryTree.o \
|
||||||
|
$(objdir)SPARQLquery.o $(objdir)Varset.o $(objdir)KVstore.o $(objdir)ResultFilter.o $(objdir)Strategy.o $(objdir)StringIndex.o
|
||||||
|
$(CC) $(CFLAGS) Query/GeneralEvaluation.cpp $(inc) -o $(objdir)GeneralEvaluation.o
|
||||||
|
|
||||||
|
#$(objdir)SIStorage.o: KVstore/SITree/storage/SIStorage.cpp KVstore/SITree/storage/SIStorage.h Util/Util.h
|
||||||
|
#$(CC) $(CFLAGS) KVstore/SITree/storage/SIStorage.cpp -o $(objdir)SIStorage.o $(def64IO)
|
||||||
|
|
||||||
|
#$(objdir)ISStorage.o: KVstore/ISTree/storage/ISStorage.cpp KVstore/ISTree/storage/ISStorage.h Util/Util.h
|
||||||
|
#$(CC) $(CFLAGS) KVstore/ISTree/storage/ISStorage.cpp -o $(objdir)ISStorage.o $(def64IO)
|
||||||
|
|
||||||
|
#$(objdir)VSTree.o $(objdir)VSTree.o: VSTree/VSTree.cpp VSTree/VSTree.h $(objdir)EntryBuffer.o $(objdir)LRUCache.o $(objdir)VNode.o
|
||||||
|
#$(CC) $(CFLAGS) VSTree/VSTree.cpp $(inc) -o $(objdir)VSTree.o $(def64IO)
|
||||||
|
|
||||||
|
#$(objdir)EntryBuffer.o: VSTree/EntryBuffer.cpp VSTree/EntryBuffer.h Signature/SigEntry.h
|
||||||
|
#$(CC) $(CFLAGS) VSTree/EntryBuffer.cpp $(inc) -o $(objdir)EntryBuffer.o $(def64IO)
|
||||||
|
|
||||||
|
#$(objdir)LRUCache.o: VSTree/LRUCache.cpp VSTree/LRUCache.h VSTree/VNode.h
|
||||||
|
#$(CC) $(CFLAGS) VSTree/LRUCache.cpp $(inc) -o $(objdir)LRUCache.o $(def64IO)
|
||||||
|
|
||||||
|
#$(objdir)VNode.o: VSTree/VNode.cpp VSTree/VNode.h
|
||||||
|
#$(CC) $(CFLAGS) VSTree/VNode.cpp $(inc) -o $(objdir)VNode.o $(def64IO)
|
||||||
|
|
||||||
|
|
||||||
|
$(lib_antlr):
|
||||||
|
rm -rf tools/libantlr3c-3.4/
|
||||||
|
cd tools; tar -xzvf libantlr3c-3.4.tar.gz;
|
||||||
|
cd tools; cd libantlr3c-3.4/; ./configure -enable-64bit; make;
|
||||||
|
rm -rf lib/libantlr.a
|
||||||
|
ar -crv lib/libantlr.a tools/libantlr3c-3.4/*.o
|
||||||
|
#NOTICE: update the sparql.tar.gz if Sparql* in Parser are changed manually
|
||||||
|
rm -rf Parser/Sparql*
|
||||||
|
cd tools; tar -xzvf sparql.tar.gz; mv Sparql* ../Parser/;
|
||||||
|
|
||||||
|
$(api_cpp): $(objdir)Socket.o
|
||||||
|
$(MAKE) -C api/cpp/src
|
||||||
|
|
||||||
|
$(api_java):
|
||||||
|
$(MAKE) -C api/java/src
|
||||||
|
|
||||||
|
.PHONY: clean dist tarball api_example gtest sumlines
|
||||||
|
|
||||||
|
clean:
|
||||||
|
rm -rf lib/libantlr.a
|
||||||
|
$(MAKE) -C api/cpp/src clean
|
||||||
|
$(MAKE) -C api/cpp/example clean
|
||||||
|
$(MAKE) -C api/java/src clean
|
||||||
|
$(MAKE) -C api/java/example clean
|
||||||
|
#$(MAKE) -C KVstore clean
|
||||||
|
rm -rf $(exedir)g* $(objdir)*.o $(objdir)*.d $(exedir).gserver*
|
||||||
|
#rm -rf .project .cproject .settings just for eclipse
|
||||||
|
#rm -rf cscope* just for vim
|
||||||
|
find . -type f -print|grep -E "\.d"|xargs rm
|
||||||
|
|
||||||
|
dist: clean
|
||||||
|
rm -rf *.nt *.n3 .oebug/*.log .tmp/*.oat *.txt *.ob
|
||||||
|
rm -rf tools/libantlr3c-3.4 lib/libantlr.a Parser/Sparql*
|
||||||
|
#rm -rf Parser/SparqlLexer* Parser/SparlParser.cpp
|
||||||
|
rm -rf cscope* .cproject .settings tags
|
||||||
|
rm -rf *.info
|
||||||
|
|
||||||
|
tarball:
|
||||||
|
tar -czvf devGstore.tar.gz api bin lib tools .oebug .tmp .objs test docs data makefile \
|
||||||
|
Main Database KVstore Util Query Signature VSTree Parser Server README.md init.conf NOTES.md StringIndex
|
||||||
|
|
||||||
|
APIexample: $(api_cpp) $(api_java)
|
||||||
|
$(MAKE) -C api/cpp/example
|
||||||
|
$(MAKE) -C api/java/example
|
||||||
|
|
||||||
|
gtest: $(objdir)gtest.o $(objfile)
|
||||||
|
$(CC) $(EXEFLAG) -o $(exedir)gtest $(objdir)gtest.o $(objfile) lib/libantlr.a $(library)
|
||||||
|
|
||||||
|
$(objdir)gtest.o: test/gtest.cpp
|
||||||
|
$(CC) $(CFLAGS) test/gtest.cpp $(inc) -o $(objdir)gtest.o
|
||||||
|
|
||||||
|
$(exedir)gadd: $(objdir)gadd.o $(objfile)
|
||||||
|
$(CC) $(EXEFLAG) -o $(exedir)gadd $(objdir)gadd.o $(objfile) lib/libantlr.a $(library)
|
||||||
|
|
||||||
|
$(objdir)gadd.o: Main/gadd.cpp
|
||||||
|
$(CC) $(CFLAGS) Main/gadd.cpp $(inc) -o $(objdir)gadd.o
|
||||||
|
|
||||||
|
$(exedir)gsub: $(objdir)gsub.o $(objfile)
|
||||||
|
$(CC) $(EXEFLAG) -o $(exedir)gsub $(objdir)gsub.o $(objfile) lib/libantlr.a $(library)
|
||||||
|
|
||||||
|
$(objdir)gsub.o: Main/gsub.cpp
|
||||||
|
$(CC) $(CFLAGS) Main/gsub.cpp $(inc) -o $(objdir)gsub.o
|
||||||
|
|
||||||
|
sumlines:
|
||||||
|
bash test/sumline.sh
|
||||||
|
|
||||||
|
tag:
|
||||||
|
ctags -R
|
||||||
|
|
||||||
|
idx:
|
||||||
|
find `realpath .` -name "*.h" -o -name "*.c" -o -name "*.cpp" > cscope.files
|
||||||
|
cscope -bkq #-i cscope.files
|
||||||
|
|
||||||
|
cover:
|
||||||
|
bash test/cover.sh
|
||||||
|
|
||||||
|
fulltest:
|
||||||
|
#NOTICE:compile gstore with -O2 only
|
||||||
|
#setup new virtuoso and configure it
|
||||||
|
cp test/full_test.sh ~
|
||||||
|
cd ~
|
||||||
|
bash full_test.sh
|
||||||
|
|
114
test/makefile
114
test/makefile
|
@ -1,114 +0,0 @@
|
||||||
#help for make
|
|
||||||
#http://www.cnblogs.com/wang_yb/p/3990952.html
|
|
||||||
#https://segmentfault.com/a/1190000000349917
|
|
||||||
#http://blog.csdn.net/cuiyifang/article/details/7910268
|
|
||||||
|
|
||||||
|
|
||||||
#compile parameters
|
|
||||||
|
|
||||||
CC = g++
|
|
||||||
|
|
||||||
CFLAGS = -c -g -Wall
|
|
||||||
|
|
||||||
# paths
|
|
||||||
|
|
||||||
VPATH = .:Util:Main:Parser:Query:KVstore:Database:Signature:VSTree:Server
|
|
||||||
|
|
||||||
SRC_PATH = $(foreach dir, $(subst:,,$(VPATH)), $(wildcard $(dir)/,*.cpp))
|
|
||||||
|
|
||||||
OBJ_DIR = .objs/
|
|
||||||
|
|
||||||
#OBJ_PATH = $(addprefix $(OBJ_DIR)/, $(subst:,,$(VPATH)))
|
|
||||||
#MAKE_OBJECT_DIR := $(shell mkdir -p $(OBJ_DIR $(OBJ_PATH)))
|
|
||||||
|
|
||||||
OBJS = $(addprefix $(OBJ_DIR),$(subst .cpp,.o,$(SRC_PATH)))
|
|
||||||
|
|
||||||
EXE_DIR = bin/
|
|
||||||
|
|
||||||
ANTLR = lib/libantlr.a
|
|
||||||
|
|
||||||
INC = -I./tools/libantlr3c-3.4/ -I./tools/libantlr3c-3.4/INClude
|
|
||||||
|
|
||||||
#add -lreadline -ltermcap if using readline or objs contain readline
|
|
||||||
LIBRARY = -ltermcap -lreadline -L./lib -lantlr
|
|
||||||
|
|
||||||
all: $(ANTLR) $(EXE_DIR)gload $(EXE_DIR)gserver $(EXE_DIR)gclient $(EXE_DIR)gquery $(EXE_DIR)gconsole API
|
|
||||||
|
|
||||||
#executables begin
|
|
||||||
|
|
||||||
$(EXE_DIR)gload: $(OBJS) $(ANTLR)
|
|
||||||
$(CC) -g -o $@ $(OBJS) $(LIBRARY)
|
|
||||||
|
|
||||||
$(EXE_DIR)gquery: $(OBJS) $(ANTLR)
|
|
||||||
$(CC) -g -o $@ $(OBJS) $(LIBRARY)
|
|
||||||
|
|
||||||
$(EXE_DIR)gserver: $(OBJS) $(ANTLR)
|
|
||||||
$(CC) -g -o $@ $(OBJS) $(LIBRARY)
|
|
||||||
|
|
||||||
$(EXE_DIR)gclient: $(OBJS) $(ANTLR)
|
|
||||||
$(CC) -g -o $@ $(OBJS) $(LIBRARY)
|
|
||||||
|
|
||||||
$(EXE_DIR)gconsole: $(OBJS) $(ANTLR) API
|
|
||||||
$(CC) -g -o $@ $(OBJS) $(LIBRARY) -L./api/cpp/lib -lgstoreconnector
|
|
||||||
|
|
||||||
#executables end
|
|
||||||
|
|
||||||
|
|
||||||
$(OBJ_DIR)%.o: %.cpp %.cpp.d
|
|
||||||
$(CC) -o $@ $< $(INC) $(CFLAGS)
|
|
||||||
|
|
||||||
|
|
||||||
DEPS = $(OBJS:.o=cpp.d)
|
|
||||||
$(DEPS): $(OBJ_DIR)%.cpp.d: %.cpp
|
|
||||||
$(CC) $< -MM $(INC) > $(OBJ_DIR)$<.d
|
|
||||||
|
|
||||||
|
|
||||||
$(ANTLR):
|
|
||||||
rm -rf tools/libantlr3c-3.4/
|
|
||||||
cd tools; tar -xzvf libantlr3c-3.4.tar.gz;
|
|
||||||
cd tools; cd libantlr3c-3.4/; ./configure -enable-64bit; make;
|
|
||||||
rm -rf lib/libantlr.a
|
|
||||||
ar -crv lib/libantlr.a tools/libantlr3c-3.4/*.o
|
|
||||||
#NOTICE: update the sparql.tar.gz if Sparql* in Parser are changed manually
|
|
||||||
rm -rf Parser/Sparql*
|
|
||||||
cd tools; tar -xzvf sparql.tar.gz; mv Sparql* ../Parser/;
|
|
||||||
|
|
||||||
API:
|
|
||||||
$(MAKE) -C api/cpp/src
|
|
||||||
#$(MAKE) -C api/cpp/example
|
|
||||||
$(MAKE) -C api/java/src
|
|
||||||
#$(MAKE) -C api/java/example
|
|
||||||
|
|
||||||
.PHONY: clean dist tarball api_example gtest sumlines
|
|
||||||
|
|
||||||
clean:
|
|
||||||
$(MAKE) -C api/cpp/src clean
|
|
||||||
$(MAKE) -C api/cpp/example clean
|
|
||||||
$(MAKE) -C api/java/src clean
|
|
||||||
$(MAKE) -C api/java/example clean
|
|
||||||
#$(MAKE) -C KVstore clean
|
|
||||||
rm -rf $(EXE_DIR)g* $(OBJ_DIR)*.o
|
|
||||||
#rm -rf .project .cproject .settings just for eclipse
|
|
||||||
#rm -rf cscope* just for vim
|
|
||||||
|
|
||||||
dist: clean
|
|
||||||
rm -rf *.nt *.n3 .debug/*.log .tmp/*.dat *.txt *.db
|
|
||||||
rm -rf tools/libantlr3c-3.4 lib/libantlr.a Parser/Sparql*
|
|
||||||
|
|
||||||
tarball:
|
|
||||||
tar -czvf devGstore.tar.gz api bin lib tools .debug .tmp .objs test docs data makefile \
|
|
||||||
Main Database KVstore Util Query Signature VSTree Parser Server LICENSE README.md
|
|
||||||
|
|
||||||
api_example: API
|
|
||||||
$(MAKE) -C api/cpp/example
|
|
||||||
$(MAKE) -C api/java/example
|
|
||||||
|
|
||||||
gtest: $(OBJ_DIR)gtest.o $(OBJS)
|
|
||||||
$(CC) -g -o $(EXE_DIR)gtest $(OBJ_DIR)gtest.o $(OBJS) lib/libantlr.a $(LIBRARY)
|
|
||||||
|
|
||||||
$(OBJ_DIR)gtest.o: test/gtest.cpp
|
|
||||||
$(CC) $(CFLAGS) test/gtest.cpp $(INC) -o $(OBJ_DIR)gtest.o
|
|
||||||
|
|
||||||
sumlines:
|
|
||||||
bash test/sumline.sh
|
|
||||||
|
|
|
@ -0,0 +1,446 @@
|
||||||
|
#help for make
|
||||||
|
#http://www.cnblogs.com/wang_yb/p/3990952.html
|
||||||
|
#https://segmentfault.com/a/1190000000349917
|
||||||
|
#http://blog.csdn.net/cuiyifang/article/details/7910268
|
||||||
|
|
||||||
|
#to use gprof to analyse efficience of the program:
|
||||||
|
#http://blog.chinaunix.net/uid-25194149-id-3215487.html
|
||||||
|
|
||||||
|
#to use gcov and lcov
|
||||||
|
#Notice that optimization should not be used here
|
||||||
|
#http://blog.163.com/bobile45@126/blog/static/96061992201382025729313/
|
||||||
|
#gcov -a main.cpp
|
||||||
|
#lcov --directory . --capture --output-file dig.info
|
||||||
|
#genhtml --output-directory . --frames --show-details dig.info
|
||||||
|
|
||||||
|
#to use doxygen+graphviz+htmlhelp to generate document from source code:
|
||||||
|
#http://www.doxygen.nl/
|
||||||
|
#(also include good comments norm)
|
||||||
|
#http://blog.csdn.net/u010740725/article/details/51387810
|
||||||
|
|
||||||
|
#NOTICE: to speed up the make process, use make -j4
|
||||||
|
#use -j8 or higher may cause error
|
||||||
|
#http://blog.csdn.net/cscrazybing/article/details/50789482
|
||||||
|
#http://blog.163.com/liuhonggaono1@126/blog/static/10497901201210254622141/
|
||||||
|
|
||||||
|
|
||||||
|
#TODO:the dependences are not complete!
|
||||||
|
|
||||||
|
#compile parameters
|
||||||
|
|
||||||
|
CC = ccache g++
|
||||||
|
#CC = g++
|
||||||
|
|
||||||
|
#the optimazition level of gcc/g++
|
||||||
|
#http://blog.csdn.net/hit_090420216/article/details/44900215
|
||||||
|
#NOTICE: -O2 is recommended, while -O3 is dangerous
|
||||||
|
#when developing, not use -O because it will disturb the normal
|
||||||
|
#routine. use it for test and release.
|
||||||
|
#CFLAGS = -c -Wall -g #-fprofile-arcs -ftest-coverage #-pg
|
||||||
|
#EXEFLAG = -g #-fprofile-arcs -ftest-coverage #-pg
|
||||||
|
#-coverage
|
||||||
|
CFLAGS = -c -Wall -O2
|
||||||
|
EXEFLAG = -O2
|
||||||
|
|
||||||
|
#add -lreadline -ltermcap if using readline or objs contain readline
|
||||||
|
library = -ltermcap -lreadline -L./lib -lantlr -lgcov
|
||||||
|
def64IO = -D_FILE_OFFSET_BITS=64 -D_LARGEFILE64_SOURCE
|
||||||
|
|
||||||
|
# paths
|
||||||
|
|
||||||
|
objdir = .objs/
|
||||||
|
|
||||||
|
exedir = bin/
|
||||||
|
|
||||||
|
lib_antlr = lib/libantlr.a
|
||||||
|
|
||||||
|
api_cpp = api/cpp/lib/libgstoreconnector.a
|
||||||
|
|
||||||
|
api_java = api/java/lib/GstoreJavaAPI.jar
|
||||||
|
|
||||||
|
# objects
|
||||||
|
|
||||||
|
#sstreeobj = $(objdir)Tree.o $(objdir)Storage.o $(objdir)Node.o $(objdir)IntlNode.o $(objdir)LeafNode.o $(objdir)Heap.o
|
||||||
|
sitreeobj = $(objdir)SITree.o $(objdir)SIStorage.o $(objdir)SINode.o $(objdir)SIIntlNode.o $(objdir)SILeafNode.o $(objdir)SIHeap.o
|
||||||
|
istreeobj = $(objdir)ISTree.o $(objdir)ISStorage.o $(objdir)ISNode.o $(objdir)ISIntlNode.o $(objdir)ISLeafNode.o $(objdir)ISHeap.o
|
||||||
|
|
||||||
|
kvstoreobj = $(objdir)KVstore.o $(sitreeobj) $(istreeobj) #$(sstreeobj)
|
||||||
|
|
||||||
|
utilobj = $(objdir)Util.o $(objdir)Bstr.o $(objdir)Stream.o $(objdir)Triple.o $(objdir)BloomFilter.o
|
||||||
|
|
||||||
|
queryobj = $(objdir)SPARQLquery.o $(objdir)BasicQuery.o $(objdir)ResultSet.o $(objdir)IDList.o \
|
||||||
|
$(objdir)Varset.o $(objdir)QueryTree.o $(objdir)ResultFilter.o $(objdir)GeneralEvaluation.o
|
||||||
|
|
||||||
|
signatureobj = $(objdir)SigEntry.o $(objdir)Signature.o
|
||||||
|
|
||||||
|
vstreeobj = $(objdir)VSTree.o $(objdir)EntryBuffer.o $(objdir)LRUCache.o $(objdir)VNode.o
|
||||||
|
|
||||||
|
stringindexobj = $(objdir)StringIndex.o
|
||||||
|
|
||||||
|
parserobj = $(objdir)RDFParser.o $(objdir)SparqlParser.o $(objdir)DBparser.o \
|
||||||
|
$(objdir)SparqlLexer.o $(objdir)TurtleParser.o $(objdir)QueryParser.o
|
||||||
|
|
||||||
|
serverobj = $(objdir)Operation.o $(objdir)Server.o $(objdir)Client.o $(objdir)Socket.o
|
||||||
|
|
||||||
|
databaseobj = $(objdir)Database.o $(objdir)Join.o $(objdir)Strategy.o
|
||||||
|
|
||||||
|
|
||||||
|
objfile = $(kvstoreobj) $(vstreeobj) $(stringindexobj) $(parserobj) $(serverobj) $(databaseobj) \
|
||||||
|
$(utilobj) $(signatureobj) $(queryobj)
|
||||||
|
|
||||||
|
inc = -I./tools/libantlr3c-3.4/ -I./tools/libantlr3c-3.4/include
|
||||||
|
|
||||||
|
|
||||||
|
#auto generate dependencies
|
||||||
|
# http://blog.csdn.net/gmpy_tiger/article/details/51849474
|
||||||
|
# http://blog.csdn.net/jeffrey0000/article/details/12421317
|
||||||
|
|
||||||
|
#gtest
|
||||||
|
TARGET = $(exedir)gbuild $(exedir)gserver $(exedir)gclient $(exedir)gquery $(exedir)gconsole $(api_java) $(exedir)gadd $(exedir)gsub
|
||||||
|
|
||||||
|
all: $(TARGET)
|
||||||
|
|
||||||
|
test_index: test_index.cpp
|
||||||
|
$(CC) $(EXEFLAG) -o test_index test_index.cpp $(objfile) $(library)
|
||||||
|
|
||||||
|
#BETTER: use for loop to reduce the lines
|
||||||
|
#NOTICE: g++ -MM will run error if linking failed, like Database.h/../SparlParser.h/../antlr3.h
|
||||||
|
|
||||||
|
#executables begin
|
||||||
|
|
||||||
|
#NOTICE:not include g*.o in objfile due to multiple definitions of main()
|
||||||
|
$(exedir)gbuild: $(lib_antlr) $(objdir)gbuild.o $(objfile)
|
||||||
|
$(CC) $(EXEFLAG) -o $(exedir)gbuild $(objdir)gbuild.o $(objfile) $(library)
|
||||||
|
|
||||||
|
$(exedir)gquery: $(lib_antlr) $(objdir)gquery.o $(objfile)
|
||||||
|
$(CC) $(EXEFLAG) -o $(exedir)gquery $(objdir)gquery.o $(objfile) $(library)
|
||||||
|
|
||||||
|
$(exedir)gserver: $(lib_antlr) $(objdir)gserver.o $(objfile)
|
||||||
|
$(CC) $(EXEFLAG) -o $(exedir)gserver $(objdir)gserver.o $(objfile) $(library)
|
||||||
|
|
||||||
|
$(exedir)gclient: $(lib_antlr) $(objdir)gclient.o $(objfile)
|
||||||
|
$(CC) $(EXEFLAG) -o $(exedir)gclient $(objdir)gclient.o $(objfile) $(library)
|
||||||
|
|
||||||
|
$(exedir)gconsole: $(lib_antlr) $(objdir)gconsole.o $(objfile) $(api_cpp)
|
||||||
|
$(CC) $(EXEFLAG) -o $(exedir)gconsole $(objdir)gconsole.o $(objfile) $(library) -L./api/cpp/lib -lgstoreconnector
|
||||||
|
|
||||||
|
#executables end
|
||||||
|
|
||||||
|
|
||||||
|
#objects in Main/ begin
|
||||||
|
|
||||||
|
$(objdir)gbuild.o: Main/gbuild.cpp Database/Database.h Util/Util.h $(lib_antlr)
|
||||||
|
$(CC) $(CFLAGS) Main/gbuild.cpp $(inc) -o $(objdir)gbuild.o
|
||||||
|
|
||||||
|
$(objdir)gquery.o: Main/gquery.cpp Database/Database.h Util/Util.h $(lib_antlr)
|
||||||
|
$(CC) $(CFLAGS) Main/gquery.cpp $(inc) -o $(objdir)gquery.o #-DREADLINE_ON
|
||||||
|
#add -DREADLINE_ON if using readline
|
||||||
|
|
||||||
|
$(objdir)gserver.o: Main/gserver.cpp Server/Server.h Util/Util.h $(lib_antlr)
|
||||||
|
$(CC) $(CFLAGS) Main/gserver.cpp $(inc) -o $(objdir)gserver.o
|
||||||
|
|
||||||
|
$(objdir)gclient.o: Main/gclient.cpp Server/Client.h Util/Util.h $(lib_antlr)
|
||||||
|
$(CC) $(CFLAGS) Main/gclient.cpp $(inc) -o $(objdir)gclient.o #-DREADLINE_ON
|
||||||
|
|
||||||
|
$(objdir)gconsole.o: Main/gconsole.cpp Database/Database.h Util/Util.h api/cpp/src/GstoreConnector.h $(lib_antlr)
|
||||||
|
$(CC) $(CFLAGS) Main/gconsole.cpp $(inc) -o $(objdir)gconsole.o -I./api/cpp/src/ #-DREADLINE_ON
|
||||||
|
|
||||||
|
#objects in Main/ end
|
||||||
|
|
||||||
|
|
||||||
|
#objects in kvstore/ begin
|
||||||
|
|
||||||
|
#objects in sstree/ begin
|
||||||
|
#$(objdir)Tree.o: KVstore/SSTree/Tree.cpp KVstore/SSTree/Tree.h $(objdir)Stream.o
|
||||||
|
#$(CC) $(CFLAGS) KVstore/SSTree/Tree.cpp -o $(objdir)Tree.o
|
||||||
|
|
||||||
|
#$(objdir)Storage.o: KVstore/SSTree/storage/Storage.cpp KVstore/SSTree/storage/Storage.h $(objdir)Util.o
|
||||||
|
#$(CC) $(CFLAGS) KVstore/SSTree/storage/Storage.cpp -o $(objdir)Storage.o $(def64IO)
|
||||||
|
|
||||||
|
#$(objdir)Node.o: KVstore/SSTree/node/Node.cpp KVstore/SSTree/node/Node.h $(objdir)Util.o
|
||||||
|
#$(CC) $(CFLAGS) KVstore/SSTree/node/Node.cpp -o $(objdir)Node.o
|
||||||
|
|
||||||
|
#$(objdir)IntlNode.o: KVstore/SSTree/node/IntlNode.cpp KVstore/SSTree/node/IntlNode.h
|
||||||
|
#$(CC) $(CFLAGS) KVstore/SSTree/node/IntlNode.cpp -o $(objdir)IntlNode.o
|
||||||
|
|
||||||
|
#$(objdir)LeafNode.o: KVstore/SSTree/node/LeafNode.cpp KVstore/SSTree/node/LeafNode.h
|
||||||
|
#$(CC) $(CFLAGS) KVstore/SSTree/node/LeafNode.cpp -o $(objdir)LeafNode.o
|
||||||
|
|
||||||
|
#$(objdir)Heap.o: KVstore/SSTree/heap/Heap.cpp KVstore/SSTree/heap/Heap.h $(objdir)Util.o
|
||||||
|
#$(CC) $(CFLAGS) KVstore/SSTree/heap/Heap.cpp -o $(objdir)Heap.o
|
||||||
|
#objects in sstree/ end
|
||||||
|
|
||||||
|
#objects in sitree/ begin
|
||||||
|
$(objdir)SITree.o: KVstore/SITree/SITree.cpp KVstore/SITree/SITree.h $(objdir)Stream.o
|
||||||
|
$(CC) $(CFLAGS) KVstore/SITree/SITree.cpp -o $(objdir)SITree.o
|
||||||
|
|
||||||
|
$(objdir)SIStorage.o: KVstore/SITree/storage/SIStorage.cpp KVstore/SITree/storage/SIStorage.h $(objdir)Util.o
|
||||||
|
$(CC) $(CFLAGS) KVstore/SITree/storage/SIStorage.cpp -o $(objdir)SIStorage.o $(def64IO)
|
||||||
|
|
||||||
|
$(objdir)SINode.o: KVstore/SITree/node/SINode.cpp KVstore/SITree/node/SINode.h $(objdir)Util.o
|
||||||
|
$(CC) $(CFLAGS) KVstore/SITree/node/SINode.cpp -o $(objdir)SINode.o
|
||||||
|
|
||||||
|
$(objdir)SIIntlNode.o: KVstore/SITree/node/SIIntlNode.cpp KVstore/SITree/node/SIIntlNode.h
|
||||||
|
$(CC) $(CFLAGS) KVstore/SITree/node/SIIntlNode.cpp -o $(objdir)SIIntlNode.o
|
||||||
|
|
||||||
|
$(objdir)SILeafNode.o: KVstore/SITree/node/SILeafNode.cpp KVstore/SITree/node/SILeafNode.h
|
||||||
|
$(CC) $(CFLAGS) KVstore/SITree/node/SILeafNode.cpp -o $(objdir)SILeafNode.o
|
||||||
|
|
||||||
|
$(objdir)SIHeap.o: KVstore/SITree/heap/SIHeap.cpp KVstore/SITree/heap/SIHeap.h $(objdir)Util.o
|
||||||
|
$(CC) $(CFLAGS) KVstore/SITree/heap/SIHeap.cpp -o $(objdir)SIHeap.o
|
||||||
|
#objects in sitree/ end
|
||||||
|
|
||||||
|
#objects in istree/ begin
|
||||||
|
$(objdir)ISTree.o: KVstore/ISTree/ISTree.cpp KVstore/ISTree/ISTree.h $(objdir)Stream.o
|
||||||
|
$(CC) $(CFLAGS) KVstore/ISTree/ISTree.cpp -o $(objdir)ISTree.o
|
||||||
|
|
||||||
|
$(objdir)ISStorage.o: KVstore/ISTree/storage/ISStorage.cpp KVstore/ISTree/storage/ISStorage.h $(objdir)Util.o
|
||||||
|
$(CC) $(CFLAGS) KVstore/ISTree/storage/ISStorage.cpp -o $(objdir)ISStorage.o $(def64IO)
|
||||||
|
|
||||||
|
$(objdir)ISNode.o: KVstore/ISTree/node/ISNode.cpp KVstore/ISTree/node/ISNode.h $(objdir)Util.o
|
||||||
|
$(CC) $(CFLAGS) KVstore/ISTree/node/ISNode.cpp -o $(objdir)ISNode.o
|
||||||
|
|
||||||
|
$(objdir)ISIntlNode.o: KVstore/ISTree/node/ISIntlNode.cpp KVstore/ISTree/node/ISIntlNode.h
|
||||||
|
$(CC) $(CFLAGS) KVstore/ISTree/node/ISIntlNode.cpp -o $(objdir)ISIntlNode.o
|
||||||
|
|
||||||
|
$(objdir)ISLeafNode.o: KVstore/ISTree/node/ISLeafNode.cpp KVstore/ISTree/node/ISLeafNode.h
|
||||||
|
$(CC) $(CFLAGS) KVstore/ISTree/node/ISLeafNode.cpp -o $(objdir)ISLeafNode.o
|
||||||
|
|
||||||
|
$(objdir)ISHeap.o: KVstore/ISTree/heap/ISHeap.cpp KVstore/ISTree/heap/ISHeap.h $(objdir)Util.o
|
||||||
|
$(CC) $(CFLAGS) KVstore/ISTree/heap/ISHeap.cpp -o $(objdir)ISHeap.o
|
||||||
|
#objects in istree/ end
|
||||||
|
|
||||||
|
$(objdir)KVstore.o: KVstore/KVstore.cpp KVstore/KVstore.h KVstore/Tree.h
|
||||||
|
$(CC) $(CFLAGS) KVstore/KVstore.cpp $(inc) -o $(objdir)KVstore.o
|
||||||
|
|
||||||
|
#objects in kvstore/ end
|
||||||
|
|
||||||
|
|
||||||
|
#objects in Database/ begin
|
||||||
|
|
||||||
|
$(objdir)Database.o: Database/Database.cpp Database/Database.h \
|
||||||
|
$(objdir)IDList.o $(objdir)ResultSet.o $(objdir)SPARQLquery.o \
|
||||||
|
$(objdir)BasicQuery.o $(objdir)Triple.o $(objdir)SigEntry.o \
|
||||||
|
$(objdir)KVstore.o $(objdir)VSTree.o $(objdir)DBparser.o \
|
||||||
|
$(objdir)Util.o $(objdir)RDFParser.o $(objdir)Join.o $(objdir)GeneralEvaluation.o $(objdir)StringIndex.o
|
||||||
|
$(CC) $(CFLAGS) Database/Database.cpp $(inc) -o $(objdir)Database.o
|
||||||
|
|
||||||
|
$(objdir)Join.o: Database/Join.cpp Database/Join.h $(objdir)IDList.o $(objdir)BasicQuery.o $(objdir)Util.o\
|
||||||
|
$(objdir)KVstore.o $(objdir)Util.o $(objdir)SPARQLquery.o
|
||||||
|
$(CC) $(CFLAGS) Database/Join.cpp $(inc) -o $(objdir)Join.o
|
||||||
|
|
||||||
|
$(objdir)Strategy.o: Database/Strategy.cpp Database/Strategy.h $(objdir)SPARQLquery.o $(objdir)BasicQuery.o \
|
||||||
|
$(objdir)Triple.o $(objdir)IDList.o $(objdir)KVstore.o $(objdir)VSTree.o $(objdir)Util.o $(objdir)Join.o $(objdir)ResultFilter.o
|
||||||
|
$(CC) $(CFLAGS) Database/Strategy.cpp $(inc) -o $(objdir)Strategy.o
|
||||||
|
|
||||||
|
#objects in Database/ end
|
||||||
|
|
||||||
|
|
||||||
|
#objects in Query/ begin
|
||||||
|
|
||||||
|
$(objdir)IDList.o: Query/IDList.cpp Query/IDList.h
|
||||||
|
$(CC) $(CFLAGS) Query/IDList.cpp $(inc) -o $(objdir)IDList.o
|
||||||
|
|
||||||
|
$(objdir)SPARQLquery.o: Query/SPARQLquery.cpp Query/SPARQLquery.h $(objdir)BasicQuery.o
|
||||||
|
$(CC) $(CFLAGS) Query/SPARQLquery.cpp $(inc) -o $(objdir)SPARQLquery.o
|
||||||
|
|
||||||
|
$(objdir)BasicQuery.o: Query/BasicQuery.cpp Query/BasicQuery.h $(objdir)Signature.o
|
||||||
|
$(CC) $(CFLAGS) Query/BasicQuery.cpp $(inc) -o $(objdir)BasicQuery.o
|
||||||
|
|
||||||
|
$(objdir)ResultSet.o: Query/ResultSet.cpp Query/ResultSet.h $(objdir)Stream.o
|
||||||
|
$(CC) $(CFLAGS) Query/ResultSet.cpp $(inc) -o $(objdir)ResultSet.o
|
||||||
|
|
||||||
|
$(objdir)Varset.o: Query/Varset.cpp Query/Varset.h
|
||||||
|
$(CC) $(CFLAGS) Query/Varset.cpp $(inc) -o $(objdir)Varset.o
|
||||||
|
|
||||||
|
$(objdir)QueryTree.o: Query/QueryTree.cpp Query/QueryTree.h $(objdir)Varset.o
|
||||||
|
$(CC) $(CFLAGS) Query/QueryTree.cpp $(inc) -o $(objdir)QueryTree.o
|
||||||
|
|
||||||
|
$(objdir)ResultFilter.o: Query/ResultFilter.cpp Query/ResultFilter.h $(objdir)BasicQuery.o $(objdir)SPARQLquery.o $(objdir)Util.o
|
||||||
|
$(CC) $(CFLAGS) Query/ResultFilter.cpp $(inc) -o $(objdir)ResultFilter.o
|
||||||
|
|
||||||
|
#no more using $(objdir)Database.o
|
||||||
|
$(objdir)GeneralEvaluation.o: Query/GeneralEvaluation.cpp Query/GeneralEvaluation.h $(objdir)QueryParser.o $(objdir)QueryTree.o \
|
||||||
|
$(objdir)SPARQLquery.o $(objdir)Varset.o $(objdir)KVstore.o $(objdir)ResultFilter.o $(objdir)Strategy.o $(objdir)StringIndex.o
|
||||||
|
$(CC) $(CFLAGS) Query/GeneralEvaluation.cpp $(inc) -o $(objdir)GeneralEvaluation.o
|
||||||
|
|
||||||
|
#objects in Query/ end
|
||||||
|
|
||||||
|
|
||||||
|
#objects in Signature/ begin
|
||||||
|
|
||||||
|
$(objdir)SigEntry.o: Signature/SigEntry.cpp Signature/SigEntry.h $(objdir)Signature.o
|
||||||
|
$(CC) $(CFLAGS) Signature/SigEntry.cpp $(inc) -o $(objdir)SigEntry.o
|
||||||
|
|
||||||
|
$(objdir)Signature.o: Signature/Signature.cpp Signature/Signature.h
|
||||||
|
$(CC) $(CFLAGS) Signature/Signature.cpp $(inc) -o $(objdir)Signature.o
|
||||||
|
|
||||||
|
#objects in Signature/ end
|
||||||
|
|
||||||
|
|
||||||
|
#objects in Util/ begin
|
||||||
|
|
||||||
|
$(objdir)Util.o: Util/Util.cpp Util/Util.h
|
||||||
|
$(CC) $(CFLAGS) Util/Util.cpp -o $(objdir)Util.o
|
||||||
|
|
||||||
|
$(objdir)Stream.o: Util/Stream.cpp Util/Stream.h $(objdir)Util.o $(objdir)Bstr.o
|
||||||
|
$(CC) $(CFLAGS) Util/Stream.cpp -o $(objdir)Stream.o $(def64IO)
|
||||||
|
|
||||||
|
$(objdir)Bstr.o: Util/Bstr.cpp Util/Bstr.h $(objdir)Util.o
|
||||||
|
$(CC) $(CFLAGS) Util/Bstr.cpp -o $(objdir)Bstr.o
|
||||||
|
|
||||||
|
$(objdir)Triple.o: Util/Triple.cpp Util/Triple.h $(objdir)Util.o
|
||||||
|
$(CC) $(CFLAGS) Util/Triple.cpp -o $(objdir)Triple.o
|
||||||
|
|
||||||
|
$(objdir)BloomFilter.o: Util/BloomFilter.cpp Util/BloomFilter.h $(objdir)Util.o
|
||||||
|
$(CC) $(CFLAGS) Util/BloomFilter.cpp -o $(objdir)BloomFilter.o
|
||||||
|
|
||||||
|
#objects in util/ end
|
||||||
|
|
||||||
|
|
||||||
|
#objects in VSTree/ begin
|
||||||
|
|
||||||
|
$(objdir)VSTree.o: VSTree/VSTree.cpp VSTree/VSTree.h $(objdir)EntryBuffer.o $(objdir)LRUCache.o $(objdir)VNode.o
|
||||||
|
$(CC) $(CFLAGS) VSTree/VSTree.cpp $(inc) -o $(objdir)VSTree.o $(def64IO)
|
||||||
|
|
||||||
|
$(objdir)EntryBuffer.o: VSTree/EntryBuffer.cpp VSTree/EntryBuffer.h Signature/SigEntry.h
|
||||||
|
$(CC) $(CFLAGS) VSTree/EntryBuffer.cpp $(inc) -o $(objdir)EntryBuffer.o $(def64IO)
|
||||||
|
|
||||||
|
$(objdir)LRUCache.o: VSTree/LRUCache.cpp VSTree/LRUCache.h VSTree/VNode.h
|
||||||
|
$(CC) $(CFLAGS) VSTree/LRUCache.cpp $(inc) -o $(objdir)LRUCache.o $(def64IO)
|
||||||
|
|
||||||
|
$(objdir)VNode.o: VSTree/VNode.cpp VSTree/VNode.h
|
||||||
|
$(CC) $(CFLAGS) VSTree/VNode.cpp $(inc) -o $(objdir)VNode.o $(def64IO)
|
||||||
|
|
||||||
|
#objects in VSTree/ end
|
||||||
|
|
||||||
|
|
||||||
|
#objects in StringIndex/ begin
|
||||||
|
$(objdir)StringIndex.o: StringIndex/StringIndex.cpp StringIndex/StringIndex.h $(objdir)KVstore.o $(objdir)Util.o
|
||||||
|
|
||||||
|
$(CC) $(CFLAGS) StringIndex/StringIndex.cpp $(inc) -o $(objdir)StringIndex.o
|
||||||
|
#objects in StringIndex/ end
|
||||||
|
|
||||||
|
|
||||||
|
#objects in Parser/ begin
|
||||||
|
|
||||||
|
$(objdir)DBparser.o: Parser/DBparser.cpp Parser/DBparser.h $(objdir)SparqlParser.o $(objdir)SparqlLexer.o $(objdir)Triple.o
|
||||||
|
$(CC) $(CFLAGS) Parser/DBparser.cpp $(inc) -o $(objdir)DBparser.o
|
||||||
|
|
||||||
|
$(objdir)SparqlParser.o: Parser/SparqlParser.c Parser/SparqlParser.h
|
||||||
|
gcc $(CFLAGS) Parser/SparqlParser.c $(inc) -o $(objdir)SparqlParser.o
|
||||||
|
|
||||||
|
$(objdir)SparqlLexer.o: Parser/SparqlLexer.c Parser/SparqlLexer.h
|
||||||
|
gcc $(CFLAGS) Parser/SparqlLexer.c $(inc) -o $(objdir)SparqlLexer.o
|
||||||
|
|
||||||
|
$(objdir)TurtleParser.o: Parser/TurtleParser.cpp Parser/TurtleParser.h Parser/Type.h
|
||||||
|
gcc $(CFLAGS) Parser/TurtleParser.cpp $(inc) -o $(objdir)TurtleParser.o
|
||||||
|
|
||||||
|
$(objdir)RDFParser.o: Parser/RDFParser.cpp Parser/RDFParser.h $(objdir)TurtleParser.o $(objdir)Triple.o
|
||||||
|
gcc $(CFLAGS) Parser/RDFParser.cpp $(inc) -o $(objdir)RDFParser.o
|
||||||
|
|
||||||
|
$(objdir)QueryParser.o: Parser/QueryParser.cpp Parser/QueryParser.h $(objdir)SparqlParser.o $(objdir)SparqlLexer.o $(objdir)QueryTree.o
|
||||||
|
$(CC) $(CFLAGS) Parser/QueryParser.cpp $(inc) -o $(objdir)QueryParser.o
|
||||||
|
|
||||||
|
#objects in Parser/ end
|
||||||
|
|
||||||
|
|
||||||
|
#objects in Server/ begin
|
||||||
|
|
||||||
|
$(objdir)Operation.o: Server/Operation.cpp Server/Operation.h
|
||||||
|
$(CC) $(CFLAGS) Server/Operation.cpp $(inc) -o $(objdir)Operation.o
|
||||||
|
|
||||||
|
$(objdir)Socket.o: Server/Socket.cpp Server/Socket.h
|
||||||
|
$(CC) $(CFLAGS) Server/Socket.cpp $(inc) -o $(objdir)Socket.o
|
||||||
|
|
||||||
|
$(objdir)Server.o: Server/Server.cpp Server/Server.h $(objdir)Socket.o $(objdir)Database.o $(objdir)Operation.o
|
||||||
|
$(CC) $(CFLAGS) Server/Server.cpp $(inc) -o $(objdir)Server.o
|
||||||
|
|
||||||
|
$(objdir)Client.o: Server/Client.cpp Server/Client.h $(objdir)Socket.o $(objdir)Util.o
|
||||||
|
$(CC) $(CFLAGS) Server/Client.cpp $(inc) -o $(objdir)Client.o
|
||||||
|
|
||||||
|
#objects in Server/ end
|
||||||
|
|
||||||
|
|
||||||
|
$(lib_antlr):
|
||||||
|
rm -rf tools/libantlr3c-3.4/
|
||||||
|
cd tools; tar -xzvf libantlr3c-3.4.tar.gz;
|
||||||
|
cd tools; cd libantlr3c-3.4/; ./configure -enable-64bit; make;
|
||||||
|
rm -rf lib/libantlr.a
|
||||||
|
ar -crv lib/libantlr.a tools/libantlr3c-3.4/*.o
|
||||||
|
#NOTICE: update the sparql.tar.gz if Sparql* in Parser are changed manually
|
||||||
|
rm -rf Parser/Sparql*
|
||||||
|
cd tools; tar -xzvf sparql.tar.gz; mv Sparql* ../Parser/;
|
||||||
|
|
||||||
|
$(api_cpp): $(objdir)Socket.o
|
||||||
|
$(MAKE) -C api/cpp/src
|
||||||
|
|
||||||
|
$(api_java):
|
||||||
|
$(MAKE) -C api/java/src
|
||||||
|
|
||||||
|
.PHONY: clean dist tarball api_example gtest sumlines
|
||||||
|
|
||||||
|
clean:
|
||||||
|
rm -rf lib/libantlr.a
|
||||||
|
$(MAKE) -C api/cpp/src clean
|
||||||
|
$(MAKE) -C api/cpp/example clean
|
||||||
|
$(MAKE) -C api/java/src clean
|
||||||
|
$(MAKE) -C api/java/example clean
|
||||||
|
#$(MAKE) -C KVstore clean
|
||||||
|
rm -rf $(exedir)g* $(objdir)*.o $(exedir).gserver*
|
||||||
|
#rm -rf .project .cproject .settings just for eclipse
|
||||||
|
#rm -rf cscope* just for vim
|
||||||
|
|
||||||
|
dist: clean
|
||||||
|
rm -rf *.nt *.n3 .debug/*.log .tmp/*.dat *.txt *.db
|
||||||
|
rm -rf tools/libantlr3c-3.4 lib/libantlr.a Parser/Sparql*
|
||||||
|
#rm -rf Parser/SparqlLexer* Parser/SparlParser.cpp
|
||||||
|
rm -rf cscope* .cproject .settings tags
|
||||||
|
rm -rf *.info
|
||||||
|
|
||||||
|
tarball:
|
||||||
|
tar -czvf devGstore.tar.gz api bin lib tools .debug .tmp .objs test docs data makefile \
|
||||||
|
Main Database KVstore Util Query Signature VSTree Parser Server README.md init.conf NOTES.md StringIndex
|
||||||
|
|
||||||
|
APIexample: $(api_cpp) $(api_java)
|
||||||
|
$(MAKE) -C api/cpp/example
|
||||||
|
$(MAKE) -C api/java/example
|
||||||
|
|
||||||
|
gtest: $(objdir)gtest.o $(objfile)
|
||||||
|
$(CC) $(EXEFLAG) -o $(exedir)gtest $(objdir)gtest.o $(objfile) lib/libantlr.a $(library)
|
||||||
|
|
||||||
|
$(objdir)gtest.o: test/gtest.cpp
|
||||||
|
$(CC) $(CFLAGS) test/gtest.cpp $(inc) -o $(objdir)gtest.o
|
||||||
|
|
||||||
|
$(exedir)gadd: $(objdir)gadd.o $(objfile)
|
||||||
|
$(CC) $(EXEFLAG) -o $(exedir)gadd $(objdir)gadd.o $(objfile) lib/libantlr.a $(library)
|
||||||
|
|
||||||
|
$(objdir)gadd.o: Main/gadd.cpp
|
||||||
|
$(CC) $(CFLAGS) Main/gadd.cpp $(inc) -o $(objdir)gadd.o
|
||||||
|
|
||||||
|
$(exedir)gsub: $(objdir)gsub.o $(objfile)
|
||||||
|
$(CC) $(EXEFLAG) -o $(exedir)gsub $(objdir)gsub.o $(objfile) lib/libantlr.a $(library)
|
||||||
|
|
||||||
|
$(objdir)gsub.o: Main/gsub.cpp
|
||||||
|
$(CC) $(CFLAGS) Main/gsub.cpp $(inc) -o $(objdir)gsub.o
|
||||||
|
|
||||||
|
sumlines:
|
||||||
|
bash test/sumline.sh
|
||||||
|
|
||||||
|
tag:
|
||||||
|
ctags -R
|
||||||
|
|
||||||
|
idx:
|
||||||
|
find `realpath .` -name "*.h" -o -name "*.c" -o -name "*.cpp" > cscope.files
|
||||||
|
cscope -bkq #-i cscope.files
|
||||||
|
|
||||||
|
cover:
|
||||||
|
bash test/cover.sh
|
||||||
|
|
||||||
|
fulltest:
|
||||||
|
#NOTICE:compile gstore with -O2 only
|
||||||
|
#setup new virtuoso and configure it
|
||||||
|
cp test/full_test.sh ~
|
||||||
|
cd ~
|
||||||
|
bash full_test.sh
|
||||||
|
|
Loading…
Reference in New Issue