changeset 614:62fbc4316d97

farray.sh: Implement falist_update(): update an existing alist from another
author Franz Glasner <fzglas.hg@dom66.de>
date Thu, 19 Sep 2024 22:20:02 +0200
parents 17194ffe3638
children 454ce7fa25c8
files share/local-bsdtools/farray.sh tests/farray-alist.t
diffstat 2 files changed, 113 insertions(+), 1 deletions(-) [+]
line wrap: on
line diff
--- a/share/local-bsdtools/farray.sh	Thu Sep 19 20:03:29 2024 +0200
+++ b/share/local-bsdtools/farray.sh	Thu Sep 19 22:20:02 2024 +0200
@@ -1541,7 +1541,7 @@
         #
         # Not yet found: "append" ..
         #
-        # NOTE: __farr_idx already the new correct length
+        # NOTE: __farr_idx here already is the new correct length
         #
         __farr_len=${__farr_idx}
         #   ... the key/value pairs to storage
@@ -1556,6 +1556,76 @@
 
 
 #:
+#: Update an alist from another alist.
+#:
+#: Key-values from the other alist are given precedence.
+#:
+#: Args:
+#:   $1 (str): The name of the alist that is to be updated.
+#:   $2 (str): The name of the other alist.
+#:
+falist_update() {
+
+    local __farr_l_name __farr_r_name
+
+    local __farr_l_token __farr_l_objname __farr_l_keyname __farr_l_valname __farr_l_len
+    local __farr_r_token __farr_r_objname __farr_r_keyname __farr_r_valname __farr_r_len
+
+    local __farr_name __farr_token __farr_objname __farr_keyname __farr_valname __farr_len
+    local __farr_l_idx __farr_r_idx __farr_r_key  __farr_l_key __farr_value
+
+    [ $# -ne 2 ] && _farr_fatal "exactly two arrays must be given"
+    _farr_alist_get_meta "$1"
+    __farr_l_name="${__farr_name}"
+    __farr_l_token="${__farr_token}"
+    __farr_l_objname="${__farr_objname}"
+    __farr_l_keyname="${__farr_keyname}"
+    __farr_l_valname="${__farr_valname}"
+    __farr_l_len="${__farr_len}"
+    _farr_alist_get_meta "$2"
+    __farr_r_name="${__farr_name}"
+    __farr_r_token="${__farr_token}"
+    __farr_r_objname="${__farr_objname}"
+    __farr_r_keyname="${__farr_keyname}"
+    __farr_r_valname="${__farr_valname}"
+    __farr_r_len="${__farr_len}"
+
+    __farr_r_idx=1
+    while [ ${__farr_r_idx} -le ${__farr_r_len} ]; do
+        eval __farr_r_key=\"\$\{${__farr_r_keyname}_${__farr_r_idx}\}\"
+
+        __farr_l_idx=1
+        while [ ${__farr_l_idx} -le ${__farr_l_len} ]; do
+            eval __farr_l_key=\"\$\{${__farr_l_keyname}_${__farr_l_idx}\}\"
+            if [ "${__farr_l_key}" = "${__farr_r_key}" ]; then
+                eval __farr_value=\"\$\{${__farr_r_valname}_${__farr_r_idx}\}\"
+                eval ${__farr_l_valname}_${__farr_l_idx}=\"\$\{__farr_value\}\"
+                break
+            fi
+            __farr_l_idx=$((__farr_l_idx + 1))
+        done
+        #
+        # If __farr_l_idx > __farr_l_len: Not yet found: "append" ..
+        #
+        # NOTE: __farr_l_idx is here also the new correct length
+        #
+        if [ ${__farr_l_idx} -eq $((__farr_l_len + 1)) ]; then
+            #   ... the key/value pairs to storage
+            eval ${__farr_l_keyname}_${__farr_l_idx}=\"\$\{__farr_r_key\}\"
+            eval __farr_value=\"\$\{${__farr_r_valname}_${__farr_r_idx}\}\"
+            eval ${__farr_l_valname}_${__farr_l_idx}=\"\$\{__farr_value\}\"
+            #   ... the new length in storage
+            eval ${__farr_l_objname}__=${__farr_l_idx}
+            #   ... and temporary here
+            __farr_l_len=${__farr_l_idx}
+        fi
+        __farr_r_idx=$((__farr_r_idx + 1))
+    done
+    return 0
+}
+
+
+#:
 #: Get the value that is associated with a key and put it into a variable.
 #:
 #: Args:
--- a/tests/farray-alist.t	Thu Sep 19 20:03:29 2024 +0200
+++ b/tests/farray-alist.t	Thu Sep 19 22:20:02 2024 +0200
@@ -273,4 +273,46 @@
   $ falist_destroy LIST3
   $ falist_destroy LIST4
 
+  $ check_no_alist_artifacts
+
+
+Updating
+========
+
+  $ falist_create ARR "Key 1" "Value 1" "Key 2" 'Value 2 '\'''
+  $ falist_create UPDATE1 "Key 1" "Value 1" "Key 2" 'Value 2 '\'''
+  $ falist_create UPDATE2 "Key 2" 'Value 2 (Updated) '\''' "Key 3" "Value 3"
+  $ falist_create EMPTY
+
+  $ falist_are_equal_with_order ARR UPDATE1
+  $ falist_are_equal_with_order ARR UPDATE2
+  [1]
+
+  $ falist_update ARR UPDATE1
+  $ falist_are_equal_with_order ARR UPDATE1
+
+  $ falist_update ARR UPDATE2
+  $ falist_debug ARR
+  DEBUG: alist `ARR' has length 3
+  DEBUG:     `Key 1' -> `Value 1'
+  DEBUG:     `Key 2' -> `Value 2 (Updated) ''
+  DEBUG:     `Key 3' -> `Value 3'
+
+Updating an into an empty alist is just a copy
+
+  $ falist_update EMPTY UPDATE1
+  $ falist_debug EMPTY
+  DEBUG: alist `EMPTY' has length 2
+  DEBUG:     `Key 1' -> `Value 1'
+  DEBUG:     `Key 2' -> `Value 2 ''
+  $ falist_debug UPDATE1
+  DEBUG: alist `UPDATE1' has length 2
+  DEBUG:     `Key 1' -> `Value 1'
+  DEBUG:     `Key 2' -> `Value 2 ''
+
+  $ falist_destroy ARR
+  $ falist_destroy UPDATE1
+  $ falist_destroy UPDATE2
+  $ falist_destroy EMPTY
+
   $ check_no_alist_artifacts
\ No newline at end of file