BASH关联阵列排序



如果我想分别在bash中传递关联数组的键和值,并使用了

之类的东西
./foo.py -k "${!args[@]}" -v "${args[@]}"

他们会以相同的顺序出现吗?我真的不在乎其他k = v对存储了什么,但是我确实需要知道我是否可以依靠键和值出现,以使密钥数组中的第三项实际上是钥匙值数组中的第三项。

我知道关联阵列是"无序的",无论您将它们添加到数组中的任何顺序与它们的输出方式无关,但是我想知道基础存储行为是否意味着它们始终以相同的顺序输出。

似乎答案是肯定的,基于我在bash版本4.3, assoc.c中找到的代码,键和值将始终处于相同的顺序上。数组的键和值分别由函数assoc_keys_to_word_listassoc_to_word_list检索。这两个函数在两种情况下都运行相同循环的assoc_to_word_list_internal,并且仅根据t参数重述的项目类型(行482-503):

>
static WORD_LIST *
assoc_to_word_list_internal (h, t)
     HASH_TABLE *h;
     int t;
{
  WORD_LIST *list;
  int i;
  BUCKET_CONTENTS *tlist;
  char *w;
  if (h == 0 || assoc_empty (h))
    return((WORD_LIST *)NULL);
  list = (WORD_LIST *)NULL;
  for (i = 0; i < h->nbuckets; i++)
    for (tlist = hash_items (i, h); tlist; tlist = tlist->next)
      {
  w = (t == 0) ? (char *)tlist->data : (char *)tlist->key;
  list = make_word_list (make_bare_word(w), list);
      }
  return (REVERSE_LIST(list, WORD_LIST *));
}

如果您想知道make_word_listarray.c/h中定义。它只是将新的WORD_LIST节点附加到现有链接列表中。

虽然这没有提供您期望的行为始终支持的合同保证,但至少目前可以安全地使用您的呼叫惯例,这是一个很好的迹象。关联阵列仅是bash的事实,使实现更多地是有效的参考。

数组不是解决此问题的解决方案,尤其是不是关联数组。即使他们确实按照相同的顺序出现,您也会有多个钥匙单-K选项,导致语法错误。阵列也是A&nbsp; bashism,而不是由Posix定义。更好的解决方案就是这样:

./foo.py -k key1,key2,key3 -v val1,val2,val3

那么,python肯定可以拆分输入字符串?我做了类似的事情使用Posix Shell:

tr , 'n' > keys <<eof
$1
eof
tr , 'n' > vals <<eof
$2
eof
paste -d 'n' keys values |
while
  read key
  read val
do
  printf 'key: %s, val: %sn' "$key" "$val"
done

当然,对于Python来说,这会容易得多,因为您可以将字符串直接进入数组而无需使用文件。

最新更新