代码之家  ›  专栏  ›  技术社区  ›  Ben Blank Jarret Hardie

按lua中的值对表进行关联排序

  •  20
  • Ben Blank Jarret Hardie  · 技术社区  · 15 年前

    我有一个key=>值表,我想用lua排序。键都是整数,但不是连续的(并且有意义)。Lua唯一的排序功能似乎是 table.sort ,它将表视为简单数组,丢弃原始键及其与特定项的关联。相反,我基本上希望能够使用 PHP's asort() 功能。

    我所拥有的:

    items = {
        [1004] = "foo",
        [1234] = "bar",
        [3188] = "baz",
        [7007] = "quux",
    }
    

    排序操作后需要的内容:

    items = {
        [1234] = "bar",
        [3188] = "baz",
        [1004] = "foo",
        [7007] = "quux",
    }
    

    有什么想法吗?

    编辑: 基于答案,我假设这只是我正在使用的特定嵌入式Lua解释器的一个奇怪的怪癖,但是在我所有的测试中, pairs() 总是按添加到表中的顺序返回表项。(即上述两个声明的迭代方式不同)。

    不幸的是,因为这不是正常的行为,看起来我无法得到我需要的;Lua没有必要的内置工具(当然),而且嵌入式环境太有限,我无法解决它。

    不过,谢谢你的帮助!

    6 回复  |  直到 9 年前
        1
  •  36
  •   DifferentPseudonym Kornel Kisielewicz    9 年前

    你好像误解了什么。这里有一个 associative array . 关联数组在它们上面没有明确的顺序,例如,只有内部表示(通常是排序的)对它们排序。

    简而言之——在Lua中,您发布的两个数组都是 相同的 .

    相反,你想要的是这样一种表现:

    items = {
        {1004, "foo"},
        {1234, "bar"},
        {3188, "baz"},
        {7007, "quux"},
    }
    

    虽然你现在不能通过索引获得它们(它们被索引为1,2,3,4,但是你 可以 创建另一个索引数组),可以使用 table.sort .

    排序函数将是:

    function compare(a,b)
      return a[1] < b[1]
    end
    
    table.sort(items, compare)
    
        2
  •  8
  •   Karl    11 年前

    正如Komel所说,您要处理的是联合数组,它没有保证的顺序。

    如果您希望在保留关联数组功能的同时基于其关联值进行键排序,可以执行以下操作:

    function getKeysSortedByValue(tbl, sortFunction)
      local keys = {}
      for key in pairs(tbl) do
        table.insert(keys, key)
      end
    
      table.sort(keys, function(a, b)
        return sortFunction(tbl[a], tbl[b])
      end)
    
      return keys
    end
    
    items = {
        [1004] = "foo",
        [1234] = "bar",
        [3188] = "baz",
        [7007] = "quux",
    }
    
    local sortedKeys = getKeysSortedByValue(items, function(a, b) return a < b end)
    

    SortedKeys是1234318810047007,您可以这样访问数据:

    for _, key in ipairs(sortedKeys) do
      print(key, items[key])
    end
    

    结果:

    1234     bar     
    3188     baz     
    1004     foo     
    7007     quux    
    
        3
  •  6
  •   sylvanaar    15 年前

    嗯,错过了无法控制迭代的部分。那里

    但在卢亚,通常有一种方法。

    http://lua-users.org/wiki/OrderedAssociativeTable

    这是一个开始。现在您需要替换库使用的pairs()。这可能是一个简单的配对=我的配对。然后您可以使用上面链接中的解决方案

        4
  •  3
  •   Norman Ramsey    15 年前

    PHP数组不同于Lua表。

    • PHP数组可能具有 有序表 键值对的。

    • Lua表始终包含 无序集合 键值对的。

    当程序员选择使用整数1、2、3,…作为钥匙。语言语法和标准库函数,比如 table.sort 对具有连续整数键的表提供特殊支持。

    因此,如果您想要模拟一个PHP数组,您必须使用键值对列表来表示它,这实际上是一个表表表,但是将它看作键值对列表会更有用。将自定义的“小于”函数传递给 排序 你会准备好的。

    N.B.Lua允许你 混合 连续整数键和 相同的 表和表示是有效的。我有时会使用这个特性,通常用一些元数据标记数组。

        5
  •  3
  •   Phantomwhale    14 年前

    几个月后,用同样的查询来讨论这个问题。推荐的答案似乎可以精确地指出Lua中所需的内容和它的外观之间的差距,但它并不能确切地告诉我我需要什么:这是一个按键排序的哈希。

    然而,本页的前三个功能是: http://lua-users.org/wiki/SortedIteration

        6
  •  1
  •   Carl Smotricz    15 年前

    几年前我做了一个简短的Lua编码,但我不再熟练。

    当遇到类似的问题时,我将数组复制到另一个具有反转键和值的数组,然后使用 sort 在新阵列上。

    我不知道使用Kornel-Kisilewicz推荐的方法对数组进行排序的可能性。