IndexRecord.cpp 3.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169
  1. /* ---------------------------------------------------------------------------
  2. Nullsoft Database Engine
  3. --------------------
  4. codename: Near Death Experience
  5. --------------------------------------------------------------------------- */
  6. /* ---------------------------------------------------------------------------
  7. IndexRecord Class
  8. --------------------------------------------------------------------------- */
  9. #include "../nde.h"
  10. #include <stdio.h>
  11. IndexRecord::IndexRecord(int RecordPos, int insertionPoint, VFILE *TableHandle, Table *ParentTable)
  12. {
  13. InsertionPoint = insertionPoint;
  14. if (RecordPos != 0)
  15. {
  16. int n=0;
  17. uint32_t ThisPos = RecordPos;
  18. while (ThisPos)
  19. {
  20. if (n >= 128)
  21. break;
  22. Vfseek(TableHandle, ThisPos, SEEK_SET);
  23. Field Entry (ThisPos);
  24. Field *TypedEntry = Entry.ReadField(ParentTable, ThisPos, &ThisPos);
  25. if (!TypedEntry) break; // some db error?
  26. AddField(TypedEntry);
  27. // ThisPos = TypedEntry->GetNextFieldPos();
  28. n++;
  29. }
  30. }
  31. }
  32. void IndexRecord::BuildCollaboration()
  33. {
  34. for (FieldList::iterator itr = Fields.begin(); itr != Fields.end(); itr++)
  35. {
  36. IndexField *p = (IndexField *)(* itr);
  37. if ((itr + 1) != Fields.end())
  38. p->index->Colaborate((IndexField *)(*(itr+1)));
  39. else
  40. p->index->Colaborate((IndexField *)*(Fields.begin()));
  41. }
  42. }
  43. bool IndexRecord::NeedFix()
  44. {
  45. for (FieldList::iterator itr=Fields.begin();itr!=Fields.end();itr++)
  46. {
  47. IndexField *p = (IndexField *)*itr;
  48. if (p->index->NeedFix())
  49. return true;
  50. }
  51. return false;
  52. }
  53. IndexField *IndexRecord::GetIndexByName(const wchar_t *name)
  54. {
  55. for (FieldList::iterator itr=Fields.begin();itr!=Fields.end();itr++)
  56. {
  57. IndexField *p = (IndexField *)*itr;
  58. if (!_wcsicmp(p->GetIndexName(), name))
  59. return p;
  60. }
  61. return NULL;
  62. }
  63. bool IndexRecord::CheckIndexing(int v)
  64. {
  65. int i = v;
  66. for (FieldList::iterator itr=Fields.begin();itr!=Fields.end();itr++)
  67. {
  68. IndexField *p = (IndexField *)*itr;
  69. v = p->index->GetCooperative(v);
  70. }
  71. return v == i;
  72. }
  73. Field *RecordBase::GetField( unsigned char ID )
  74. {
  75. for ( FieldList::iterator itr = Fields.begin(); itr != Fields.end(); itr++ )
  76. {
  77. IndexField *p = (IndexField *)*itr;
  78. if ( p->GetFieldId() == ID )
  79. return p;
  80. }
  81. return NULL;
  82. }
  83. void RecordBase::AddField(Field *field)
  84. {
  85. if (!field)
  86. return;
  87. if (GetField(field->ID))
  88. return;
  89. Fields.push_back(field);
  90. }
  91. int IndexRecord::WriteFields( Table *ParentTable )
  92. {
  93. Field *l_previous_field = NULL;
  94. IndexField *l_index_field = NULL;
  95. for ( FieldList::iterator itr = Fields.begin(); itr != Fields.end(); itr++ )
  96. {
  97. l_index_field = (IndexField *)(* itr);
  98. Field* nextField = (itr + 1) != Fields.end() ? *(itr + 1) : nullptr;
  99. //l_index_field->WriteField(ParentTable, l_previous_field, (Field*)l_index_field->next);
  100. l_index_field->WriteField(ParentTable, l_previous_field, nextField);
  101. l_previous_field = l_index_field;
  102. }
  103. return WriteIndex( ParentTable );
  104. }
  105. int IndexRecord::WriteIndex( Table *ParentTable )
  106. {
  107. int P = 0;
  108. if ( !Fields.empty() )
  109. P = ( *Fields.begin() )->GetFieldPos();
  110. return ParentTable->index->Update( INDEX_RECORD_NUM, P, this, FALSE );
  111. }
  112. void RecordBase::RemoveField(Field *field)
  113. {
  114. if (!field)
  115. return;
  116. //Fields.erase(field);
  117. //delete field;
  118. for (auto it = Fields.begin(); it != Fields.end(); it++)
  119. {
  120. Field* f = *it;
  121. if (f == field)
  122. {
  123. Fields.erase(it);
  124. delete f;
  125. break;
  126. }
  127. }
  128. }
  129. void IndexRecord::WalkFields(FieldsWalker callback, void *context)
  130. {
  131. if (callback)
  132. {
  133. for (FieldList::iterator itr=Fields.begin();itr!=Fields.end();itr++)
  134. {
  135. if (!callback(this, *itr, context))
  136. break;
  137. }
  138. }
  139. }