تنفيذ Trie استنادًا إلى "HAT-trie: بنية بيانات مستندة إلى Trie واعية لذاكرة التخزين المؤقت للسلاسل." (أسكيتيس نيكولاس وسينها رانجان، 2007) ورقة. في الوقت الحالي، تم تنفيذ HAT-trie فقط، وقد تصل النسخة الهجينة لاحقًا. يمكن العثور على التفاصيل المتعلقة ببنية بيانات HAT-trie هنا.
توفر المكتبة طريقة فعالة ومدمجة لتخزين مجموعة أو خريطة من السلاسل عن طريق ضغط البادئات الشائعة. كما يسمح أيضًا بالبحث عن المفاتيح التي تطابق البادئة. لاحظ أنه على الرغم من أن المعلمات الافتراضية للبنية موجهة نحو تحسين عمليات البحث الدقيقة، إذا قمت بإجراء الكثير من عمليات البحث عن البادئات، فقد ترغب في تقليل عتبة الاندفاع من خلال طريقة burst_threshold
.
إنها بنية مكيفة بشكل جيد لتخزين عدد كبير من السلاسل.
بالنسبة لجزء تجزئة المصفوفة، يتم استخدام مشروع تجزئة المصفوفة وإدراجه في المستودع.
توفر المكتبة فئتين: tsl::htrie_map
و tsl::htrie_set
.
tsl::hat_trie
من CMakeLists.txt.equal_prefix_range
(مفيدة للإكمال التلقائي على سبيل المثال) ومسح البادئات من خلال erase_prefix
.longest_prefix
.serialize/deserialize
في واجهة برمجة التطبيقات للحصول على التفاصيل).max_load_factor
. سيؤدي عامل التحميل الأقصى الأقل إلى زيادة السرعة، وسيؤدي العامل الأعلى إلى تقليل استخدام الذاكرة. تم تعيين قيمته الافتراضية على 8.0.burst_threshold
.KeySizeT
.تشبه ضمانات سلامة الخيط والاستثناءات حاويات STL.
تعتمد وظيفة التجزئة الافتراضية التي تستخدمها البنية على وجود std::string_view
. إذا كان متاحًا، فسيتم استخدام std::hash<std::string_view>
، وإلا يتم استخدام دالة تجزئة FNV-1a بسيطة لتجنب أي تبعية.
إذا لم تتمكن من استخدام C++ 17 أو الإصدارات الأحدث، فنوصي باستبدال وظيفة التجزئة بشيء مثل CityHash، وMurmurHash، وFarmHash، ... للحصول على أداء أفضل. في الاختبارات التي أجريناها، يقدم CityHash64 تحسنًا بنسبة 20% تقريبًا في القراءات مقارنةً بـ FNV-1a.
# include < city.h >
struct str_hash {
std:: size_t operator ()( const char * key, std:: size_t key_size) const {
return CityHash64 (key, key_size);
}
};
tsl::htrie_map< char , int , str_hash> map;
لا يمكن استخدام std::hash<std::string>
بكفاءة لأن البنية لا تخزن أي كائن std::string
>. في أي وقت قد تكون هناك حاجة إلى تجزئة، يجب إنشاء std::string
.
يتكون المعيار من إدراج جميع العناوين من مساحة الاسم الرئيسية لأرشيف ويكيبيديا في بنية البيانات، والتحقق من مساحة الذاكرة المستخدمة بعد الإدراج (بما في ذلك تجزئة الذاكرة المحتملة) والبحث عن جميع العناوين مرة أخرى في بنية البيانات. يتم أيضًا قياس ذروة استخدام الذاكرة أثناء عملية الإدراج مع مرور الوقت (1).
يرتبط كل عنوان بـ int (32 بت). تستخدم جميع الهياكل القائمة على التجزئة CityHash64 كوظيفة تجزئة. بالنسبة للاختبارات التي تحمل علامة احتياطي ، يتم استدعاء وظيفة reserve
مسبقًا لتجنب أي تكرار.
لاحظ أن tsl::hopscotch_map
و std::unordered_map
و google::dense_hash_map
و spp::sparse_hash_map
يستخدمون std::string
كمفتاح يفرض حدًا أدنى لحجم 32 بايت (على نظام x64) حتى لو كان المفتاح يتكون من حرف واحد فقط. قد تكون الهياكل الأخرى قادرة على تخزين مفاتيح مكونة من حرف واحد مع 1 بايت + 8 بايت للمؤشر (على x64).
تم تجميع المعيار باستخدام الإصدار 6.3 من مجلس التعاون الخليجي وتم تشغيله على نظام Debian Stretch x64 مع معالج Intel i5-5200u وذاكرة الوصول العشوائي 8Go. تم أخذ أفضل 20 جولة.
يمكن العثور على رمز المعيار على Gist.
تم فرز مجموعة البيانات enwiki-20170320-all-titles-in-ns0.gz أبجديًا. بالنسبة لهذا المعيار، نقوم أولاً بتبديل مجموعة البيانات من خلال shuf(1) لتجنب مجموعة البيانات المصنفة المتحيزة.
مكتبة | بنية البيانات | ذاكرة الذروة (ميجابايت) | الذاكرة (ميجابايت) | إدراج (نس/مفتاح) | قراءة (نس/مفتاح) |
---|---|---|---|---|---|
tsl::htrie_map | قبعة تري | 405.22 | 402.25 | 643.10 | 250.87 |
tsl::htrie_map max_load_factor=4 | قبعة تري | 471.85 | 468.50 | 638.66 | 212.90 |
tsl::htrie_map max_load_factor=2 | قبعة تري | 569.76 | 566.52 | 630.61 | 201.10 |
tsl::htrie_map max_load_factor=1 | قبعة تري | 713.44 | 709.81 | 645.76 | 190.87 |
الارز::دا | محاولة صفيف مزدوج | 1269.68 | 1254.41 | 1102.93 | 557.20 |
الارز::da ORDERED=false | محاولة صفيف مزدوج | 1269.80 | 1254.41 | 1089.78 | 570.13 |
الارز::دا | محاولة تخفيض صفيف مزدوج | 1183.07 | 1167.79 | 1076.68 | 645.79 |
الارز::da ORDERED=false | محاولة تخفيض صفيف مزدوج | 1183.14 | 1167.85 | 1065.43 | 641.98 |
الارز::دا | بادئة صفيف مزدوج حاول | 498.69 | 496.54 | 1096.90 | 628.01 |
الارز::da ORDERED=false | بادئة صفيف مزدوج حاول | 498.65 | 496.60 | 1048.40 | 628.94 |
هات تري 1 (ج) | قبعة تري | 504.07 | 501.50 | 917.49 | 261.00 |
كيو بي تري (C) | محاولة قطر للبترول | 941.23 | 938.17 | 1349.25 | 1281.46 |
تري بت الحرجة (C) | محاولة بت الحرجة | 1074.96 | 1071.98 | 2930.42 | 2869.74 |
جوديSL (C) | مصفوفة جودي | 631.09 | 628.37 | 884.29 | 803.58 |
جودي إتش إس (ج) | مصفوفة جودي | 723.44 | 719.47 | 476.79 | 417.15 |
tsl::array_map | جدول تجزئة المصفوفة | 823.54 | 678.73 | 603.94 | 138.24 |
tsl::array_map مع الاحتياط | جدول تجزئة المصفوفة | 564.26 | 555.91 | 249.52 | 128.28 |
tsl::hopscotch_map | جدول التجزئة | 1325.83 | 1077.99 | 368.26 | 119.49 |
tsl::hopscotch_map مع الاحتياط | جدول التجزئة | 1080.51 | 1077.98 | 240.58 | 119.91 |
جوجل ::dense_hash_map | جدول التجزئة | 2319.40 | 1677.11 | 466.60 | 138.87 |
جوجل ::dense_hash_map مع الاحتياط | جدول التجزئة | 1592.51 | 1589.99 | 259.56 | 120.40 |
spp::sparse_hash_map | جدول التجزئة متفرق | 918.67 | 917.10 | 769.00 | 175.59 |
spp::sparse_hash_map مع الاحتياط | جدول التجزئة متفرق | 913.35 | 910.65 | 427.22 | 159.08 |
الأمراض المنقولة جنسيا::unordered_map | جدول التجزئة | 1249.05 | 1246.60 | 590.88 | 173.58 |
الأمراض المنقولة جنسيا::unordered_map مع الاحتياط | جدول التجزئة | 1212.23 | 1209.71 | 350.33 | 178.70 |
يتم إدخال المفتاح وقراءته بالترتيب الأبجدي.
مكتبة | بنية البيانات | ذاكرة الذروة (ميجابايت) | الذاكرة (ميجابايت) | إدراج (نس/مفتاح) | قراءة (نس/مفتاح) |
---|---|---|---|---|---|
tsl::htrie_map | قبعة تري | 396.10 | 393.22 | 255.76 | 68.08 |
tsl::htrie_map max_load_factor=4 | قبعة تري | 465.02 | 461.80 | 248.88 | 59.23 |
tsl::htrie_map max_load_factor=2 | قبعة تري | 543.99 | 541.21 | 230.13 | 53.50 |
tsl::htrie_map max_load_factor=1 | قبعة تري | 692.29 | 689.70 | 243.84 | 49.22 |
الارز::دا | محاولة صفيف مزدوج | 1269.58 | 1254.41 | 278.51 | 54.72 |
الارز::da ORDERED=false | محاولة صفيف مزدوج | 1269.66 | 1254.41 | 264.43 | 56.02 |
الارز::دا | محاولة تخفيض صفيف مزدوج | 1183.01 | 1167.78 | 254.60 | 69.18 |
الارز::da ORDERED=false | محاولة تخفيض صفيف مزدوج | 1183.03 | 1167.78 | 241.45 | 69.67 |
الارز::دا | بادئة صفيف مزدوج حاول | 621.59 | 619.38 | 246.88 | 57.83 |
الارز::da ORDERED=false | بادئة صفيف مزدوج حاول | 621.59 | 619.38 | 187.98 | 58.56 |
هات تري 2 (ج) | قبعة تري | 521.25 | 518.52 | 503.01 | 86.40 |
كيو بي تري (C) | محاولة قطر للبترول | 940.65 | 937.66 | 392.86 | 190.19 |
تري بت الحرجة (C) | محاولة بت الحرجة | 1074.87 | 1071.98 | 430.04 | 347.60 |
جوديSL (C) | مصفوفة جودي | 616.95 | 614.27 | 279.07 | 114.47 |
جودي إتش إس (ج) | مصفوفة جودي | 722.29 | 719.47 | 439.66 | 372.25 |
tsl::array_map | جدول تجزئة المصفوفة | 826.98 | 682.99 | 612.31 | 139.16 |
tsl::array_map مع الاحتياط | جدول تجزئة المصفوفة | 565.37 | 555.35 | 246.55 | 126.32 |
tsl::hopscotch_map | جدول التجزئة | 1331.87 | 1078.02 | 375.19 | 118.08 |
tsl::hopscotch_map مع الاحتياط | جدول التجزئة | 1080.51 | 1077.97 | 238.93 | 117.20 |
جوجل ::dense_hash_map | جدول التجزئة | 2325.27 | 1683.07 | 483.95 | 137.09 |
جوجل ::dense_hash_map مع الاحتياط | جدول التجزئة | 1592.54 | 1589.99 | 257.22 | 113.71 |
spp::sparse_hash_map | جدول التجزئة متفرق | 920.96 | 918.70 | 772.03 | 176.64 |
spp::sparse_hash_map مع الاحتياط | جدول التجزئة متفرق | 914.84 | 912.47 | 422.85 | 158.73 |
الأمراض المنقولة جنسيا::unordered_map | جدول التجزئة | 1249.09 | 1246.65 | 594.85 | 173.54 |
الأمراض المنقولة جنسيا::unordered_map مع الاحتياط | جدول التجزئة | 1212.21 | 1209.71 | 347.40 | 176.49 |
يتكون المعيار من إدراج جميع الكلمات من مجموعة بيانات "السلاسل المميزة" الخاصة بـ Dr. Askitis في بنية البيانات، والتحقق من مساحة الذاكرة المستخدمة والبحث عن جميع الكلمات من مجموعة بيانات "Skew String Set 1" (حيث يمكن وضع سلسلة تقديم عدة مرات) في بنية البيانات. لاحظ أن السلاسل الموجودة في مجموعة البيانات هذه لها متوسط قصير جدًا وطول متوسط للمفتاح (والتي قد لا تكون حالة استخدام واقعية مقارنة بمجموعة بيانات ويكيبيديا المستخدمة أعلاه). إنه مشابه لتلك الموجودة على صفحة الأرز الرئيسية.
البروتوكول القياسي هو نفسه المستخدم في مجموعة بيانات ويكيبيديا.
مكتبة | بنية البيانات | ذاكرة الذروة (ميجابايت) | الذاكرة (ميجابايت) | إدراج (نس/مفتاح) | قراءة (نس/مفتاح) |
---|---|---|---|---|---|
tsl::htrie_map | قبعة تري | 604.76 | 601.79 | 485.45 | 77.80 |
tsl::htrie_map max_load_factor=4 | قبعة تري | 768.10 | 764.98 | 491.78 | 75.48 |
tsl::htrie_map max_load_factor=2 | قبعة تري | 1002.42 | 999.34 | 496.78 | 72.53 |
tsl::htrie_map max_load_factor=1 | قبعة تري | 1344.98 | 1341.97 | 520.66 | 72.45 |
الارز::دا | محاولة صفيف مزدوج | 1105.45 | 1100.05 | 682.25 | 71.98 |
الارز::da ORDERED=false | محاولة صفيف مزدوج | 1105.47 | 1100.05 | 668.75 | 71.95 |
الارز::دا | محاولة تخفيض صفيف مزدوج | 941.16 | 926.04 | 684.38 | 79.11 |
الارز::da ORDERED=false | محاولة تخفيض صفيف مزدوج | 941.16 | 925.98 | 672.14 | 79.02 |
الارز::دا | بادئة صفيف مزدوج حاول | 714.58 | 712.59 | 831.71 | 75.83 |
الارز::da ORDERED=false | بادئة صفيف مزدوج حاول | 714.66 | 712.31 | 786.93 | 75.89 |
هات تري 3 (ج) | قبعة تري | 786.93 | 784.32 | 743.34 | 93.58 |
كيو بي تري (C) | محاولة قطر للبترول | 1800.02 | 1797.21 | 987.95 | 428.51 |
تري بت الحرجة (C) | محاولة بت الحرجة | 2210.52 | 2207.64 | 1986.19 | 1109.88 |
جوديSL (C) | مصفوفة جودي | 1025.59 | 1023.11 | 535.02 | 202.36 |
جودي إتش إس (ج) | مصفوفة جودي | 1002.50 | 999.97 | 456.09 | 148.36 |
tsl::array_map | جدول تجزئة المصفوفة | 1308.08 | 1031.67 | 545.82 | 46.41 |
tsl::array_map مع الاحتياط | جدول تجزئة المصفوفة | 979.44 | 921.363 | 244.19 | 45.74 |
tsl::hopscotch_map | جدول التجزئة | 2336.39 | 1611.54 | 288.70 | 47.05 |
tsl::hopscotch_map مع الاحتياط | جدول التجزئة | 1614.22 | 1611.64 | 220.67 | 46.39 |
جوجل ::dense_hash_map | جدول التجزئة | 3913.64 | 2636.31 | 317.66 | 43.62 |
جوجل ::dense_hash_map مع الاحتياط | جدول التجزئة | 2638.19 | 2635.68 | 227.58 | 43.09 |
spp::sparse_hash_map | جدول التجزئة متفرق | 1419.69 | 1417.61 | 586.26 | 56.00 |
spp::sparse_hash_map مع الاحتياط | جدول التجزئة متفرق | 1424.21 | 1421.69 | 392.76 | 55.73 |
الأمراض المنقولة جنسيا::unordered_map | جدول التجزئة | 2112.66 | 2110.19 | 554.02 | 105.05 |
الأمراض المنقولة جنسيا::unordered_map مع الاحتياط | جدول التجزئة | 2053.95 | 2051.67 | 309.06 | 109.89 |
لاستخدام المكتبة، ما عليك سوى إضافة دليل التضمين إلى مسار التضمين الخاص بك. إنها مكتبة رأسية فقط .
إذا كنت تستخدم CMake، فيمكنك أيضًا استخدام الهدف المُصدَّر tsl::hat_trie
من CMakeLists.txt مع target_link_libraries
.
# Example where the hat-trie project is stored in a third-party directory
add_subdirectory (third-party/hat-trie)
target_link_libraries (your_target PRIVATE tsl::hat_trie)
يجب أن تعمل التعليمات البرمجية مع أي مترجم متوافق مع معيار C++ 11 وقد تم اختبارها مع دول مجلس التعاون الخليجي 4.8.4، Clang 3.5.0 وVisual Studio 2015.
لإجراء الاختبارات، ستحتاج إلى مكتبة Boost Test وCMake.
git clone https://github.com/Tessil/hat-trie.git
cd hat-trie/tests
mkdir build
cd build
cmake ..
cmake --build .
./tsl_hat_trie_tests
يمكن العثور على واجهة برمجة التطبيقات هنا. إذا كان std::string_view
متاحًا، فستتغير واجهة برمجة التطبيقات قليلاً ويمكن العثور عليها هنا.
# include < iostream >
# include < string >
# include < tsl/htrie_map.h >
# include < tsl/htrie_set.h >
int main () {
/*
* Map of strings to int having char as character type.
* There is no support for wchar_t, char16_t or char32_t yet,
* but UTF-8 strings will work fine.
*/
tsl::htrie_map< char , int > map = {{ " one " , 1 }, { " two " , 2 }};
map[ " three " ] = 3 ;
map[ " four " ] = 4 ;
map. insert ( " five " , 5 );
map. insert_ks ( " six_with_extra_chars_we_ignore " , 3 , 6 );
map. erase ( " two " );
/*
* Due to the compression on the common prefixes, the letters of the string
* are not always stored contiguously. When we retrieve the key, we have to
* construct it.
*
* To avoid a heap-allocation at each iteration (when SSO doesn't occur),
* we reuse the key_buffer to construct the key.
*/
std::string key_buffer;
for ( auto it = map. begin (); it != map. end (); ++it) {
it. key (key_buffer);
std::cout << " { " << key_buffer << " , " << it. value () << " } " << std::endl;
}
/*
* If you don't care about the allocation.
*/
for ( auto it = map. begin (); it != map. end (); ++it) {
std::cout << " { " << it. key () << " , " << *it << " } " << std::endl;
}
tsl::htrie_map< char , int > map2 = {{ " apple " , 1 }, { " mango " , 2 }, { " apricot " , 3 },
{ " mandarin " , 4 }, { " melon " , 5 }, { " macadamia " , 6 }};
// Prefix search
auto prefix_range = map2. equal_prefix_range ( " ma " );
// {mandarin, 4} {mango, 2} {macadamia, 6}
for ( auto it = prefix_range. first ; it != prefix_range. second ; ++it) {
std::cout << " { " << it. key () << " , " << *it << " } " << std::endl;
}
// Find longest match prefix.
auto longest_prefix = map2. longest_prefix ( " apple juice " );
if (longest_prefix != map2. end ()) {
// {apple, 1}
std::cout << " { " << longest_prefix. key () << " , "
<< *longest_prefix << " } " << std::endl;
}
// Prefix erase
map2. erase_prefix ( " ma " );
// {apricot, 3} {melon, 5} {apple, 1}
for ( auto it = map2. begin (); it != map2. end (); ++it) {
std::cout << " { " << it. key () << " , " << *it << " } " << std::endl;
}
tsl::htrie_set< char > set = { " one " , " two " , " three " };
set. insert ({ " four " , " five " });
// {one} {two} {five} {four} {three}
for ( auto it = set. begin (); it != set. end (); ++it) {
it. key (key_buffer);
std::cout << " { " << key_buffer << " } " << std::endl;
}
}
توفر المكتبة طريقة فعالة لإجراء تسلسل وإلغاء تسلسل خريطة أو مجموعة بحيث يمكن حفظها في ملف أو إرسالها عبر الشبكة. وللقيام بذلك، يتطلب الأمر من المستخدم توفير كائن دالة لكل من التسلسل وإلغاء التسلسل.
struct serializer {
// Must support the following types for U: std::uint64_t, float and T if a map is used.
template < typename U>
void operator ()( const U& value);
void operator ()( const CharT* value, std:: size_t value_size);
};
struct deserializer {
// Must support the following types for U: std::uint64_t, float and T if a map is used.
template < typename U>
U operator ()();
void operator ()(CharT* value_out, std:: size_t value_size);
};
لاحظ أن التنفيذ يترك التوافق الثنائي (endianness، التمثيل الثنائي العائم، حجم int، ...) للأنواع التي يقوم بتسلسلها/إلغاء تسلسلها في أيدي كائنات الوظيفة المتوفرة إذا كان التوافق مطلوبًا.
يمكن العثور على مزيد من التفاصيل بشأن طرق serialize
deserialize
في واجهة برمجة التطبيقات.
# include < cassert >
# include < cstdint >
# include < fstream >
# include < type_traits >
# include < tsl/htrie_map.h >
class serializer {
public:
serializer ( const char * file_name) {
m_ostream. exceptions (m_ostream. badbit | m_ostream. failbit );
m_ostream. open (file_name);
}
template < class T ,
typename std::enable_if<std::is_arithmetic<T>::value>::type* = nullptr >
void operator ()( const T& value) {
m_ostream. write ( reinterpret_cast < const char *>(&value), sizeof (T));
}
void operator ()( const char * value, std:: size_t value_size) {
m_ostream. write (value, value_size);
}
private:
std::ofstream m_ostream;
};
class deserializer {
public:
deserializer ( const char * file_name) {
m_istream. exceptions (m_istream. badbit | m_istream. failbit | m_istream. eofbit );
m_istream. open (file_name);
}
template < class T ,
typename std::enable_if<std::is_arithmetic<T>::value>::type* = nullptr >
T operator ()() {
T value;
m_istream. read ( reinterpret_cast < char *>(&value), sizeof (T));
return value;
}
void operator ()( char * value_out, std:: size_t value_size) {
m_istream. read (value_out, value_size);
}
private:
std::ifstream m_istream;
};
int main () {
const tsl::htrie_map< char , std:: int64_t > map = {{ " one " , 1 }, { " two " , 2 },
{ " three " , 3 }, { " four " , 4 }};
const char * file_name = " htrie_map.data " ;
{
serializer serial (file_name);
map. serialize (serial);
}
{
deserializer dserial (file_name);
auto map_deserialized = tsl::htrie_map< char , std:: int64_t >:: deserialize (dserial);
assert (map == map_deserialized);
}
{
deserializer dserial (file_name);
/* *
* If the serialized and deserialized map are hash compatibles (see conditions in API),
* setting the argument to true speed-up the deserialization process as we don't have
* to recalculate the hash of each key. We also know how much space each bucket needs.
*/
const bool hash_compatible = true ;
auto map_deserialized =
tsl::htrie_map< char , std:: int64_t >:: deserialize (dserial, hash_compatible);
assert (map == map_deserialized);
}
}
من الممكن استخدام مكتبة التسلسل لتجنب بعض النماذج النموذجية إذا كانت الأنواع المطلوب إجراء تسلسل لها أكثر تعقيدًا.
يستخدم المثال التالي Boost Serialization مع تدفق ضغط Boost zlib لتقليل حجم الملف المتسلسل الناتج.
# include < boost/archive/binary_iarchive.hpp >
# include < boost/archive/binary_oarchive.hpp >
# include < boost/iostreams/filter/zlib.hpp >
# include < boost/iostreams/filtering_stream.hpp >
# include < boost/serialization/split_free.hpp >
# include < boost/serialization/utility.hpp >
# include < cassert >
# include < cstdint >
# include < fstream >
# include < tsl/htrie_map.h >
template < typename Archive>
struct serializer {
Archive& ar;
template < typename T>
void operator ()( const T& val) { ar & val; }
template < typename CharT>
void operator ()( const CharT* val, std:: size_t val_size) {
ar. save_binary ( reinterpret_cast < const void *>(val), val_size* sizeof (CharT));
}
};
template < typename Archive>
struct deserializer {
Archive& ar;
template < typename T>
T operator ()() { T val; ar & val; return val; }
template < typename CharT>
void operator ()(CharT* val_out, std:: size_t val_size) {
ar. load_binary ( reinterpret_cast < void *>(val_out), val_size* sizeof (CharT));
}
};
namespace boost { namespace serialization {
template < class Archive , class CharT , class T >
void serialize (Archive & ar, tsl::htrie_map<CharT, T>& map, const unsigned int version) {
split_free (ar, map, version);
}
template < class Archive , class CharT , class T >
void save (Archive & ar, const tsl::htrie_map<CharT, T>& map, const unsigned int version) {
serializer<Archive> serial{ar};
map. serialize (serial);
}
template < class Archive , class CharT , class T >
void load (Archive & ar, tsl::htrie_map<CharT, T>& map, const unsigned int version) {
deserializer<Archive> deserial{ar};
map = tsl::htrie_map<CharT, T>:: deserialize (deserial);
}
}}
int main () {
const tsl::htrie_map< char , std:: int64_t > map = {{ " one " , 1 }, { " two " , 2 },
{ " three " , 3 }, { " four " , 4 }};
const char * file_name = " htrie_map.data " ;
{
std::ofstream ofs;
ofs. exceptions (ofs. badbit | ofs. failbit );
ofs. open (file_name, std::ios::binary);
boost::iostreams::filtering_ostream fo;
fo. push ( boost::iostreams::zlib_compressor ());
fo. push (ofs);
boost::archive::binary_oarchive oa (fo);
oa << map;
}
{
std::ifstream ifs;
ifs. exceptions (ifs. badbit | ifs. failbit | ifs. eofbit );
ifs. open (file_name, std::ios::binary);
boost::iostreams::filtering_istream fi;
fi. push ( boost::iostreams::zlib_decompressor ());
fi. push (ifs);
boost::archive::binary_iarchive ia (fi);
tsl::htrie_map< char , std:: int64_t > map_deserialized;
ia >> map_deserialized;
assert (map == map_deserialized);
}
}
الكود مرخص بموجب ترخيص MIT، راجع ملف الترخيص للحصول على التفاصيل.