List tcl中二维列表的排序

List tcl中二维列表的排序,list,indexing,tcl,sublist,List,Indexing,Tcl,Sublist,虽然我在lsort中阅读了许多选项来实现这一点,但在我的情况下,它不起作用。 我有一个浮点数列表,如下所示 {898.465 348.700} {898.465 1511.400} {477.130 348.700} {898.465 730.200} {477.130 1511.400} {898.465 1121.400} {477.130 730.200} {477.130 1121.400} 我想按第二个索引对它进行排序,这样我就可以得到第二个索引的最小值和最大值。我尝试了下面的东西,

虽然我在lsort中阅读了许多选项来实现这一点,但在我的情况下,它不起作用。 我有一个浮点数列表,如下所示

{898.465 348.700} {898.465 1511.400} {477.130 348.700} {898.465 730.200} {477.130 1511.400} {898.465 1121.400} {477.130 730.200} {477.130 1121.400}
我想按第二个索引对它进行排序,这样我就可以得到第二个索引的最小值和最大值。我尝试了下面的东西,得到了很少的输出,但没有任何帮助

lsort -index end-1  -decreasing  `$bbox_upper`
{477.130 348.700} {477.130 1511.400} {477.130 730.200} {477.130 1121.400} {898.465 348.700} {898.465 1511.400} {898.465 730.200} {898.465 1121.400}

lsort -index 1 -real $bbox_upper
{898.465 1121.400} {477.130 1121.400} {898.465 1511.400} {477.130 1511.400} {898.465 348.700} {477.130 348.700} {898.465 730.200} {477.130 730.200}
如果您在上面的输出中看到,第二个索引1511.400是最大的,因此它应该出现在第一个子列表中,但它不会出现


您可以提供帮助吗。

您使用的是什么确切版本的Tcl(使用
info patchlevel
查找)?当我尝试使用8.6.1时,只要我使用所有需要的选项,它就可以正常工作(我也希望它可以用于任何基于8.5或8.4的Tcl):

我不会使用索引
end-1
,除非你的意思是“最后一个,但只有一个”。对于数字排序,
-real
选项是正确的<代码>-字典也可以工作,但它使用的是一种非常不同的基于字符串的算法(在文件选择器对话框中的文件名列表中向用户显示值时效果很好),对于真正的浮点数据来说效率不高


如果您需要更复杂的排序,例如当第二个值相同时,使用每对的第一个值作为tiebreak,那么您有几个选项

通常通过对数据进行两次排序来处理次关键字。这不是最有效的技术,但很容易找到正确的方法,Tcl的
lsort
使用了一种稳定的排序算法

lsort -index 1 -decreasing -real [lsort -index 0 -decreasing -real $bbox_upper]
或者,您可以使用
-command
选项将订购决策委托给您提供的某些代码:

proc sorter {aValue bValue} {
    foreach {ax ay} $aValue break
    foreach {bx by} $bValue break
    set diff [expr {$ay - $by}]
    if {$diff == 0} {
        set diff [expr {$ax - $bx}]
    }
    return [expr {$diff < 0 ? 1 : $diff > 0 ? -1 : 0}]
}
lsort -command sorter $bbox_upper
proc-sorter{aValue bValue}{
foreach{ax ay}$aValue break
foreach{bx by}$b值中断
set diff[expr{$ay-$by}]
如果{$diff==0}{
set diff[expr{$ax-$bx}]
}
返回[expr{$diff<0?1:$diff>0?-1:0}]
}
lsort-命令分拣机$bbox\U上限
从8.5开始,您可以在不引入辅助程序的情况下执行此操作:

lsort -command {apply {{aValue bValue} {
    lassign $aValue ax ay
    lassign $bValue bx by
    set diff [expr {$ay - $by}]
    if {$diff == 0} {
        set diff [expr {$ax - $bx}]
    }
    return [expr {$diff < 0 ? 1 : $diff > 0 ? -1 : 0}]
}}} $bbox_upper
lsort-命令{apply{{aValue bValue}{
lassign$aValue ax ay
lassign$B价值bx由
set diff[expr{$ay-$by}]
如果{$diff==0}{
set diff[expr{$ax-$bx}]
}
返回[expr{$diff<0?1:$diff>0?-1:0}]
}}}$bbox_上

建议您使用过程更快,而且(至少在本例中)双重排序更快。

您使用的Tcl的确切版本是什么(使用
info patchlevel
查找)?当我尝试使用8.6.1时,只要我使用所有需要的选项,它就可以正常工作(我也希望它可以用于任何基于8.5或8.4的Tcl):

我不会使用索引
end-1
,除非你的意思是“最后一个,但只有一个”。对于数字排序,
-real
选项是正确的<代码>-字典也可以工作,但它使用的是一种非常不同的基于字符串的算法(在文件选择器对话框中的文件名列表中向用户显示值时效果很好),对于真正的浮点数据来说效率不高


如果您需要更复杂的排序,例如当第二个值相同时,使用每对的第一个值作为tiebreak,那么您有几个选项

通常通过对数据进行两次排序来处理次关键字。这不是最有效的技术,但很容易找到正确的方法,Tcl的
lsort
使用了一种稳定的排序算法

lsort -index 1 -decreasing -real [lsort -index 0 -decreasing -real $bbox_upper]
或者,您可以使用
-command
选项将订购决策委托给您提供的某些代码:

proc sorter {aValue bValue} {
    foreach {ax ay} $aValue break
    foreach {bx by} $bValue break
    set diff [expr {$ay - $by}]
    if {$diff == 0} {
        set diff [expr {$ax - $bx}]
    }
    return [expr {$diff < 0 ? 1 : $diff > 0 ? -1 : 0}]
}
lsort -command sorter $bbox_upper
proc-sorter{aValue bValue}{
foreach{ax ay}$aValue break
foreach{bx by}$b值中断
set diff[expr{$ay-$by}]
如果{$diff==0}{
set diff[expr{$ax-$bx}]
}
返回[expr{$diff<0?1:$diff>0?-1:0}]
}
lsort-命令分拣机$bbox\U上限
从8.5开始,您可以在不引入辅助程序的情况下执行此操作:

lsort -command {apply {{aValue bValue} {
    lassign $aValue ax ay
    lassign $bValue bx by
    set diff [expr {$ay - $by}]
    if {$diff == 0} {
        set diff [expr {$ax - $bx}]
    }
    return [expr {$diff < 0 ? 1 : $diff > 0 ? -1 : 0}]
}}} $bbox_upper
lsort-命令{apply{{aValue bValue}{
lassign$aValue ax ay
lassign$B价值bx由
set diff[expr{$ay-$by}]
如果{$diff==0}{
set diff[expr{$ax-$bx}]
}
返回[expr{$diff<0?1:$diff>0?-1:0}]
}}}$bbox_上

建议您使用过程更快,而且(至少在本例中)双重排序更快。

您使用的Tcl的确切版本是什么(使用
info patchlevel
查找)?当我尝试使用8.6.1时,只要我使用所有需要的选项,它就可以正常工作(我也希望它可以用于任何基于8.5或8.4的Tcl):

我不会使用索引
end-1
,除非你的意思是“最后一个,但只有一个”。对于数字排序,
-real
选项是正确的<代码>-字典也可以工作,但它使用的是一种非常不同的基于字符串的算法(在文件选择器对话框中的文件名列表中向用户显示值时效果很好),对于真正的浮点数据来说效率不高


如果您需要更复杂的排序,例如当第二个值相同时,使用每对的第一个值作为tiebreak,那么您有几个选项

通常通过对数据进行两次排序来处理次关键字。这不是最有效的技术,但很容易找到正确的方法,Tcl的
lsort
使用了一种稳定的排序算法

lsort -index 1 -decreasing -real [lsort -index 0 -decreasing -real $bbox_upper]
或者,您可以使用
-command
选项将订购决策委托给您提供的某些代码:

proc sorter {aValue bValue} {
    foreach {ax ay} $aValue break
    foreach {bx by} $bValue break
    set diff [expr {$ay - $by}]
    if {$diff == 0} {
        set diff [expr {$ax - $bx}]
    }
    return [expr {$diff < 0 ? 1 : $diff > 0 ? -1 : 0}]
}
lsort -command sorter $bbox_upper
proc-sorter{aValue bValue}{
foreach{ax ay}$aValue break
foreach{bx by}$b值中断
set diff[expr{$ay-$by}]
如果{$diff==0}{
set diff[expr{$ax-$bx}]
}
返回[expr{$diff<0?1:$diff>0?-1:0}]
}
lsort-命令分拣机$bbox\U上限
从8.5开始,您可以在不引入辅助程序的情况下执行此操作:

lsort -command {apply {{aValue bValue} {
    lassign $aValue ax ay
    lassign $bValue bx by
    set diff [expr {$ay - $by}]
    if {$diff == 0} {
        set diff [expr {$ax - $bx}]
    }
    return [expr {$diff < 0 ? 1 : $diff > 0 ? -1 : 0}]
}}} $bbox_upper
lsort-命令{apply{{aValue bValue}{
lassign$aValue ax ay
lassign$B价值bx由
set diff[expr{$ay-