TableSerializer.h 8.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218
  1. /*
  2. * Copyright (c) 2014, Oculus VR, Inc.
  3. * All rights reserved.
  4. *
  5. * This source code is licensed under the BSD-style license found in the
  6. * LICENSE file in the root directory of this source tree. An additional grant
  7. * of patent rights can be found in the PATENTS file in the same directory.
  8. *
  9. */
  10. #ifndef __TABLE_SERIALIZER_H
  11. #define __TABLE_SERIALIZER_H
  12. #include "RakMemoryOverride.h"
  13. #include "DS_Table.h"
  14. #include "Export.h"
  15. namespace RakNet
  16. {
  17. class BitStream;
  18. }
  19. namespace RakNet
  20. {
  21. class RAK_DLL_EXPORT TableSerializer
  22. {
  23. public:
  24. static void SerializeTable(DataStructures::Table *in, RakNet::BitStream *out);
  25. static bool DeserializeTable(unsigned char *serializedTable, unsigned int dataLength, DataStructures::Table *out);
  26. static bool DeserializeTable(RakNet::BitStream *in, DataStructures::Table *out);
  27. static void SerializeColumns(DataStructures::Table *in, RakNet::BitStream *out);
  28. static void SerializeColumns(DataStructures::Table *in, RakNet::BitStream *out, DataStructures::List<int> &skipColumnIndices);
  29. static bool DeserializeColumns(RakNet::BitStream *in, DataStructures::Table *out);
  30. static void SerializeRow(DataStructures::Table::Row *in, unsigned keyIn, const DataStructures::List<DataStructures::Table::ColumnDescriptor> &columns, RakNet::BitStream *out);
  31. static void SerializeRow(DataStructures::Table::Row *in, unsigned keyIn, const DataStructures::List<DataStructures::Table::ColumnDescriptor> &columns, RakNet::BitStream *out, DataStructures::List<int> &skipColumnIndices);
  32. static bool DeserializeRow(RakNet::BitStream *in, DataStructures::Table *out);
  33. static void SerializeCell(RakNet::BitStream *out, DataStructures::Table::Cell *cell, DataStructures::Table::ColumnType columnType);
  34. static bool DeserializeCell(RakNet::BitStream *in, DataStructures::Table::Cell *cell, DataStructures::Table::ColumnType columnType);
  35. static void SerializeFilterQuery(RakNet::BitStream *in, DataStructures::Table::FilterQuery *query);
  36. // Note that this allocates query->cell->c!
  37. static bool DeserializeFilterQuery(RakNet::BitStream *out, DataStructures::Table::FilterQuery *query);
  38. static void SerializeFilterQueryList(RakNet::BitStream *in, DataStructures::Table::FilterQuery *query, unsigned int numQueries, unsigned int maxQueries);
  39. // Note that this allocates queries, cells, and query->cell->c!. Use DeallocateQueryList to free.
  40. static bool DeserializeFilterQueryList(RakNet::BitStream *out, DataStructures::Table::FilterQuery **query, unsigned int *numQueries, unsigned int maxQueries, int allocateExtraQueries=0);
  41. static void DeallocateQueryList(DataStructures::Table::FilterQuery *query, unsigned int numQueries);
  42. };
  43. } // namespace RakNet
  44. #endif
  45. // Test code for the table
  46. /*
  47. #include "LightweightDatabaseServer.h"
  48. #include "LightweightDatabaseClient.h"
  49. #include "TableSerializer.h"
  50. #include "BitStream.h"
  51. #include "StringCompressor.h"
  52. #include "DS_Table.h"
  53. void main(void)
  54. {
  55. DataStructures::Table table;
  56. DataStructures::Table::Row *row;
  57. unsigned int dummydata=12345;
  58. // Add columns Name (string), IP (binary), score (int), and players (int).
  59. table.AddColumn("Name", DataStructures::Table::STRING);
  60. table.AddColumn("IP", DataStructures::Table::BINARY);
  61. table.AddColumn("Score", DataStructures::Table::NUMERIC);
  62. table.AddColumn("Players", DataStructures::Table::NUMERIC);
  63. table.AddColumn("Empty Test Column", DataStructures::Table::STRING);
  64. RakAssert(table.GetColumnCount()==5);
  65. row=table.AddRow(0);
  66. RakAssert(row);
  67. row->UpdateCell(0,"Kevin Jenkins");
  68. row->UpdateCell(1,sizeof(dummydata), (char*)&dummydata);
  69. row->UpdateCell(2,5);
  70. row->UpdateCell(3,10);
  71. //row->UpdateCell(4,"should be unique");
  72. row=table.AddRow(1);
  73. row->UpdateCell(0,"Kevin Jenkins");
  74. row->UpdateCell(1,sizeof(dummydata), (char*)&dummydata);
  75. row->UpdateCell(2,5);
  76. row->UpdateCell(3,15);
  77. row=table.AddRow(2);
  78. row->UpdateCell(0,"Kevin Jenkins");
  79. row->UpdateCell(1,sizeof(dummydata), (char*)&dummydata);
  80. row->UpdateCell(2,5);
  81. row->UpdateCell(3,20);
  82. row=table.AddRow(3);
  83. RakAssert(row);
  84. row->UpdateCell(0,"Kevin Jenkins");
  85. row->UpdateCell(1,sizeof(dummydata), (char*)&dummydata);
  86. row->UpdateCell(2,15);
  87. row->UpdateCell(3,5);
  88. row->UpdateCell(4,"col index 4");
  89. row=table.AddRow(4);
  90. RakAssert(row);
  91. row->UpdateCell(0,"Kevin Jenkins");
  92. row->UpdateCell(1,sizeof(dummydata), (char*)&dummydata);
  93. //row->UpdateCell(2,25);
  94. row->UpdateCell(3,30);
  95. //row->UpdateCell(4,"should be unique");
  96. row=table.AddRow(5);
  97. RakAssert(row);
  98. row->UpdateCell(0,"Kevin Jenkins");
  99. row->UpdateCell(1,sizeof(dummydata), (char*)&dummydata);
  100. //row->UpdateCell(2,25);
  101. row->UpdateCell(3,5);
  102. //row->UpdateCell(4,"should be unique");
  103. row=table.AddRow(6);
  104. RakAssert(row);
  105. row->UpdateCell(0,"Kevin Jenkins");
  106. row->UpdateCell(1,sizeof(dummydata), (char*)&dummydata);
  107. row->UpdateCell(2,35);
  108. //row->UpdateCell(3,40);
  109. //row->UpdateCell(4,"should be unique");
  110. row=table.AddRow(7);
  111. RakAssert(row);
  112. row->UpdateCell(0,"Bob Jenkins");
  113. row=table.AddRow(8);
  114. RakAssert(row);
  115. row->UpdateCell(0,"Zack Jenkins");
  116. // Test multi-column sorting
  117. DataStructures::Table::Row *rows[30];
  118. DataStructures::Table::SortQuery queries[4];
  119. queries[0].columnIndex=0;
  120. queries[0].operation=DataStructures::Table::QS_INCREASING_ORDER;
  121. queries[1].columnIndex=1;
  122. queries[1].operation=DataStructures::Table::QS_INCREASING_ORDER;
  123. queries[2].columnIndex=2;
  124. queries[2].operation=DataStructures::Table::QS_INCREASING_ORDER;
  125. queries[3].columnIndex=3;
  126. queries[3].operation=DataStructures::Table::QS_DECREASING_ORDER;
  127. table.SortTable(queries, 4, rows);
  128. unsigned i;
  129. char out[256];
  130. RAKNET_DEBUG_PRINTF("Sort: Ascending except for column index 3\n");
  131. for (i=0; i < table.GetRowCount(); i++)
  132. {
  133. table.PrintRow(out,256,',',true, rows[i]);
  134. RAKNET_DEBUG_PRINTF("%s\n", out);
  135. }
  136. // Test query:
  137. // Don't return column 3, and swap columns 0 and 2
  138. unsigned columnsToReturn[4];
  139. columnsToReturn[0]=2;
  140. columnsToReturn[1]=1;
  141. columnsToReturn[2]=0;
  142. columnsToReturn[3]=4;
  143. DataStructures::Table resultsTable;
  144. table.QueryTable(columnsToReturn,4,0,0,&resultsTable);
  145. RAKNET_DEBUG_PRINTF("Query: Don't return column 3, and swap columns 0 and 2:\n");
  146. for (i=0; i < resultsTable.GetRowCount(); i++)
  147. {
  148. resultsTable.PrintRow(out,256,',',true, resultsTable.GetRowByIndex(i));
  149. RAKNET_DEBUG_PRINTF("%s\n", out);
  150. }
  151. // Test filter:
  152. // Only return rows with column index 4 empty
  153. DataStructures::Table::FilterQuery inclusionFilters[3];
  154. inclusionFilters[0].columnIndex=4;
  155. inclusionFilters[0].operation=DataStructures::Table::QF_IS_EMPTY;
  156. // inclusionFilters[0].cellValue; // Unused for IS_EMPTY
  157. table.QueryTable(0,0,inclusionFilters,1,&resultsTable);
  158. RAKNET_DEBUG_PRINTF("Filter: Only return rows with column index 4 empty:\n");
  159. for (i=0; i < resultsTable.GetRowCount(); i++)
  160. {
  161. resultsTable.PrintRow(out,256,',',true, resultsTable.GetRowByIndex(i));
  162. RAKNET_DEBUG_PRINTF("%s\n", out);
  163. }
  164. // Column 5 empty and column 0 == Kevin Jenkins
  165. inclusionFilters[0].columnIndex=4;
  166. inclusionFilters[0].operation=DataStructures::Table::QF_IS_EMPTY;
  167. inclusionFilters[1].columnIndex=0;
  168. inclusionFilters[1].operation=DataStructures::Table::QF_EQUAL;
  169. inclusionFilters[1].cellValue.Set("Kevin Jenkins");
  170. table.QueryTable(0,0,inclusionFilters,2,&resultsTable);
  171. RAKNET_DEBUG_PRINTF("Filter: Column 5 empty and column 0 == Kevin Jenkins:\n");
  172. for (i=0; i < resultsTable.GetRowCount(); i++)
  173. {
  174. resultsTable.PrintRow(out,256,',',true, resultsTable.GetRowByIndex(i));
  175. RAKNET_DEBUG_PRINTF("%s\n", out);
  176. }
  177. RakNet::BitStream bs;
  178. RAKNET_DEBUG_PRINTF("PreSerialize:\n");
  179. for (i=0; i < table.GetRowCount(); i++)
  180. {
  181. table.PrintRow(out,256,',',true, table.GetRowByIndex(i));
  182. RAKNET_DEBUG_PRINTF("%s\n", out);
  183. }
  184. StringCompressor::AddReference();
  185. TableSerializer::Serialize(&table, &bs);
  186. TableSerializer::Deserialize(&bs, &table);
  187. StringCompressor::RemoveReference();
  188. RAKNET_DEBUG_PRINTF("PostDeserialize:\n");
  189. for (i=0; i < table.GetRowCount(); i++)
  190. {
  191. table.PrintRow(out,256,',',true, table.GetRowByIndex(i));
  192. RAKNET_DEBUG_PRINTF("%s\n", out);
  193. }
  194. int a=5;
  195. }
  196. */
粤ICP备19079148号