diff --git a/aptos-move/framework/aptos-stdlib/doc/smart_table.md b/aptos-move/framework/aptos-stdlib/doc/smart_table.md index 0d6d81b28273b..36a51ea7205c3 100644 --- a/aptos-move/framework/aptos-stdlib/doc/smart_table.md +++ b/aptos-move/framework/aptos-stdlib/doc/smart_table.md @@ -18,6 +18,7 @@ it tolerates collisions. - [Function `new_with_config`](#0x1_smart_table_new_with_config) - [Function `destroy_empty`](#0x1_smart_table_destroy_empty) - [Function `destroy`](#0x1_smart_table_destroy) +- [Function `clear`](#0x1_smart_table_clear) - [Function `add`](#0x1_smart_table_add) - [Function `add_all`](#0x1_smart_table_add_all) - [Function `unzip_entries`](#0x1_smart_table_unzip_entries) @@ -39,6 +40,7 @@ it tolerates collisions. - [Struct `SmartTable`](#@Specification_1_SmartTable) - [Function `new_with_config`](#@Specification_1_new_with_config) - [Function `destroy`](#@Specification_1_destroy) + - [Function `clear`](#@Specification_1_clear) - [Function `add_all`](#@Specification_1_add_all) - [Function `to_simple_map`](#@Specification_1_to_simple_map) - [Function `split_one_bucket`](#@Specification_1_split_one_bucket) @@ -361,13 +363,41 @@ Destroy a table completely when V has drop.
public fun destroy<K: drop, V: drop>(table: SmartTable<K, V>) {
-    let i = 0;
+    clear(&mut table);
+    destroy_empty(table);
+}
+
+ + + + + + + +## Function `clear` + +Clear a table completely when T has drop. + + +
public fun clear<K: drop, V: drop>(table: &mut smart_table::SmartTable<K, V>)
+
+ + + +
+Implementation + + +
public fun clear<K: drop, V: drop>(table: &mut SmartTable<K, V>) {
+    *table_with_length::borrow_mut(&mut table.buckets, 0) = vector::empty();
+    let i = 1;
     while (i < table.num_buckets) {
         table_with_length::remove(&mut table.buckets, i);
         i = i + 1;
     };
-    let SmartTable { buckets, num_buckets: _, level: _, size: _, split_load_threshold: _, target_bucket_size: _ } = table;
-    table_with_length::destroy_empty(buckets);
+    table.num_buckets = 1;
+    table.level = 0;
+    table.size = 0;
 }
 
@@ -1003,7 +1033,7 @@ Update target_bucket_size. map_spec_set = spec_set, map_spec_del = spec_remove, map_spec_len = spec_len, - map_spec_has_key = spec_contains; +map_spec_has_key = spec_contains; @@ -1035,6 +1065,22 @@ Update target_bucket_size. +
pragma verify = false;
+
+ + + + + +### Function `clear` + + +
public fun clear<K: drop, V: drop>(table: &mut smart_table::SmartTable<K, V>)
+
+ + + +
pragma verify = false;
 
@@ -1083,7 +1129,7 @@ Update target_bucket_size. -
pragma verify= false;
+
pragma verify = false;
 
diff --git a/aptos-move/framework/aptos-stdlib/doc/smart_vector.md b/aptos-move/framework/aptos-stdlib/doc/smart_vector.md index 9c7ebffa32125..3d922f9742084 100644 --- a/aptos-move/framework/aptos-stdlib/doc/smart_vector.md +++ b/aptos-move/framework/aptos-stdlib/doc/smart_vector.md @@ -298,7 +298,7 @@ Aborts if v is not empty. ## Function `destroy` -Destroy a table completely when T has drop. +Destroy a vector completely when T has drop.
public fun destroy<T: drop>(v: smart_vector::SmartVector<T>)
@@ -324,6 +324,7 @@ Destroy a table completely when T has drop.
 
 ## Function `clear`
 
+Clear a vector completely when T has drop.
 
 
 
public fun clear<T: drop>(v: &mut smart_vector::SmartVector<T>)
diff --git a/aptos-move/framework/aptos-stdlib/sources/data_structures/smart_table.move b/aptos-move/framework/aptos-stdlib/sources/data_structures/smart_table.move
index acae5cbf8fbf3..d79081be0407c 100644
--- a/aptos-move/framework/aptos-stdlib/sources/data_structures/smart_table.move
+++ b/aptos-move/framework/aptos-stdlib/sources/data_structures/smart_table.move
@@ -103,13 +103,21 @@ module aptos_std::smart_table {
 
     /// Destroy a table completely when V has `drop`.
     public fun destroy(table: SmartTable) {
-        let i = 0;
+        clear(&mut table);
+        destroy_empty(table);
+    }
+
+    /// Clear a table completely when T has `drop`.
+    public fun clear(table: &mut SmartTable) {
+        *table_with_length::borrow_mut(&mut table.buckets, 0) = vector::empty();
+        let i = 1;
         while (i < table.num_buckets) {
             table_with_length::remove(&mut table.buckets, i);
             i = i + 1;
         };
-        let SmartTable { buckets, num_buckets: _, level: _, size: _, split_load_threshold: _, target_bucket_size: _ } = table;
-        table_with_length::destroy_empty(buckets);
+        table.num_buckets = 1;
+        table.level = 0;
+        table.size = 0;
     }
 
     /// Add (key, value) pair in the hash map, it may grow one bucket if current load factor exceeds the threshold.
@@ -435,4 +443,22 @@ module aptos_std::smart_table {
         assert!(simple_map::length(&map) == 200, 0);
         destroy(table);
     }
+
+    #[test]
+    public fun smart_table_clear_test() {
+        let table = new();
+        let i = 0u64;
+        while (i < 200) {
+            add(&mut table, i, i);
+            i = i + 1;
+        };
+        clear(&mut table);
+        let i = 0;
+        while (i < 200) {
+            add(&mut table, i, i);
+            i = i + 1;
+        };
+        assert!(table.size == 200, 0);
+        destroy(table);
+    }
 }
diff --git a/aptos-move/framework/aptos-stdlib/sources/data_structures/smart_table.spec.move b/aptos-move/framework/aptos-stdlib/sources/data_structures/smart_table.spec.move
index 72977552b9c60..bb7be66d622b9 100644
--- a/aptos-move/framework/aptos-stdlib/sources/data_structures/smart_table.spec.move
+++ b/aptos-move/framework/aptos-stdlib/sources/data_structures/smart_table.spec.move
@@ -15,7 +15,7 @@ spec aptos_std::smart_table {
             map_spec_set = spec_set,
             map_spec_del = spec_remove,
             map_spec_len = spec_len,
-            map_spec_has_key = spec_contains;
+        map_spec_has_key = spec_contains;
     }
 
     spec new_with_config(num_initial_buckets: u64, split_load_threshold: u8, target_bucket_size: u64): SmartTable {
@@ -26,8 +26,12 @@ spec aptos_std::smart_table {
         pragma verify = false;
     }
 
+    spec clear(table: &mut SmartTable) {
+        pragma verify = false;
+    }
+
     spec split_one_bucket(table: &mut SmartTable) {
-        pragma verify= false;
+        pragma verify = false;
     }
 
     spec bucket_index(level: u8, num_buckets: u64, hash: u64): u64 {
diff --git a/aptos-move/framework/aptos-stdlib/sources/data_structures/smart_vector.move b/aptos-move/framework/aptos-stdlib/sources/data_structures/smart_vector.move
index 2c1405b848eb0..f963057c3164a 100644
--- a/aptos-move/framework/aptos-stdlib/sources/data_structures/smart_vector.move
+++ b/aptos-move/framework/aptos-stdlib/sources/data_structures/smart_vector.move
@@ -74,12 +74,13 @@ module aptos_std::smart_vector {
         option::destroy_none(big_vec);
     }
 
-    /// Destroy a table completely when T has `drop`.
+    /// Destroy a vector completely when T has `drop`.
     public fun destroy(v: SmartVector) {
         clear(&mut v);
         destroy_empty(v);
     }
 
+    /// Clear a vector completely when T has `drop`.
     public fun clear(v: &mut SmartVector) {
         v.inline_vec = vector[];
         if (option::is_some(&v.big_vec)) {