>问题陈述
我正在从未知来源导入一组坐标,我没有权限查看该坐标。
set yMin [lindex [lindex $bbox 0] 1]
puts "yMin: <$yMin>"
它工作正常。
yMin: <-6.14999999999999e-02>
括号用于检查是否有任何空格甚至隐藏的制表符。但是,如果yMin乘以任何数字(例如 0.5),则会出错。
set Y2 [expr {0.5 * $yMin}]
不能使用空字符串作为"*">
的操作数,同时执行"expr {0.5 * $yMin}">
从"集合 Y2 [expr {0.5 * $yMin}]"中调用
即使只打印了yMin,它仍然具有空操作数错误。
set Y1 [expr $yMin]
puts "Y1: <$Y1>"
表达式 " 中的空表达式(解析表达式 ")
从"expr $yMin"中调用">
从"集合 Y1 [expr $yMin]"中调用
但是有一个有趣的测试。如果添加大括号,它就可以工作!
set Y1 [expr {$yMin}]
puts "Y1: <$Y1>"
Y1:<-0.06149999999999999999>
如何重现问题
感谢格伦·杰克曼(见下面的回复),
% set bbox {{-4.599999999999999e-02 -6.149999999999999e-02} {8.000000000000002e-02 6.149999999999999e-02}}
{-4.599999999999999e-02 -6.149999999999999e-02} {8.000000000000002e-02 6.149999999999999e-02}
% set yMin [lindex [lindex $bbox 0] 1]
-6.149999999999999e-02
% expr {1 + $yMin}
0.9385
实际上,这似乎无法重现问题(这就是我有这篇文章的原因)。但它至少可以是一个模板。
试错
以下代码用于检查它是否真的为空。事实证明它不是空的。
if {$yMin eq {}} {
puts "Empty records"
exit 1
} else {
puts "yMin is not empty: <$yMin>
}
yMin 不为空:<-6.14999999999999e-02>
最后,我尝试修剪、映射和正则表达式来删除任何空格和制表符,但它们都不起作用。
set trim_yMin [string trim $yMin]
puts "trim_yMin: <$trim_yMin>"
set map_yMin [string map {" " ""} $yMin]
puts "map_yMin: <$map_yMin>"
regsub -all {s} $yMin {} reg_yMin
puts "reg_yMin: <$reg_yMin>"
if {$trim_yMin eq {} || $map_yMin eq {} || $reg_yMin eq {}} {
puts "Empty records"
exit 1
} else {
puts "trim_yMin is not empty: <$reg_yMin>"
puts "map_yMin is not empty: <$reg_yMin>"
puts "reg_yMin is not empty: <$reg_yMin>"
}
trim_yMin:<-6.14999999999999e-02>
map_yMin:<-6.14999999999999e-02>
reg_yMin:<-6.1499999999999e-02>
trim_yMin不为空:<-6.149999999999999e-02>
map_yMin不为空:<-6.149999999999999e-02>
reg_yMin不为空:<-6.14999999999999e-02>
在这里,我只显示正则表达式的结果。其他人的结果是一样的。
set reg_Y2 [expr {0.5 * $reg_yMin}]
puts "0.5 * reg_yMin: $reg_Y2"
不能使用空字符串作为"*">
的操作数,同时执行"expr {0.5 * $reg_yMin}"从"set reg_Y2 [expr {0.5 * $reg_yMin}]">
中调用
你能帮帮我吗?我真的不知道我还能尝试什么。提前谢谢。
更新和回复
致二文:
puts $bbox;
set yMin [lindex [lindex $bbox 0] 1]
puts "yMin: <$yMin>"
{-4.599999999999999e-02 -6.149999999999999e-02} {8.0000000000000002e-026.149999999999999e-02}
yMin: <-6.14999999999999e-02>
set Y2 [expr {0.5 * $yMin}]
puts $Y2
不能使用空字符串作为"*">
的操作数,同时执行"expr {0.5 * $yMin}">
从"集合 Y2 [expr {0.5 * $yMin}]"中调用
致贝纳贾:
puts [tcl::unsupported::representation $yMin]
value 是一个引用计数为 4 的字符串,对象指针位于 0x44ed0910,内部表示形式 0x450d6120:(nil),字符串表示形式"-6.14999999999....">
对肖恩来说,
puts [tcl::unsupported::representation $yMin]
puts [binary encode hex $yMin]
puts [tcl::unsupported::representation $yMin]
puts [string is double -strict $yMin]
puts [tcl::unsupported::representation $yMin]
value 是一个字符串,refcount 为 4,对象指针位于 0x44ed6030,内部表示形式 0x450de4b0:(nil),字符串表示形式"-6.1499999999..."2D362E31343939393939393939393939652d3032
value 是一个字节数组,引用计数为 4,对象指针位于 0x44ed6030,内部表示形式0x44ee0dc0:(nil),字符串表示形式"-6.1499999999...">
1
value 是一个引用计数为 4 的双精度值,对象指针位于 0x44ed6030,内部表示形式 0xbfaf7ced916872af:(nil),字符串表示形式"-6.1499999999...">
set Y2 [expr {0.5 * -6.149999999999999e-02}]
puts "Y2: $Y2"
set new_Y2 [expr {0.5*-6.149999999999999e-02}]
puts "new_Y2: $new_Y2"
Y2: -0.03074999999999996new_Y2: -0.030749999999999996
致谢尔特·布朗,
错误消息已更改!也许它表明了什么?
puts [tcl::unsupported::representation $yMin]
set yMin " $yMin"
puts [tcl::unsupported::representation $yMin]
set Y2 [expr {0.5 * $yMin}]
puts $Y2
value 是一个字符串,引用计数为 4,对象指针位于 0x44ec28a0,内部表示形式 0x450be540:(nil),字符串表示形式"-6.1499999999...">value 是一个引用计数为 2 的字符串,对象指针位于 0x446bbc70,内部表示形式0x44695fd0:(nil),字符串表示形式" -6.149999999..."在执行"expr {0.5 * $yMin}">
时不能使用非数字字符串作为"*">
的操作数invoked from within
"set Y2 [expr {0.5 * $yMin}]">
如果在字符串为双精度严格$yMin后将值更改为双精度后计算仍然失败,则取二进制编码十六进制$yMin的结果,将其转换回字符串(使用二进制解码十六进制)并在计算中使用它。
puts "Is yMin double? : [string is double -strict $yMin]"
set binary_yMin [binary encode hex $yMin]
set double_binary_yMin [binary decode hex $binary_yMin]
puts "yMin: $yMin"
puts "Binary of double yMin: $binary_yMin"
puts "Double binary double: $double_binary_yMin"
set Y2 [expr {0.5 * $double_binary_yMin}]
puts $Y2
yMin 是双倍吗? : 1 yMin: -6.14999999999999e-02 双二进制 yMin: 2d362e3134393939393939393939393939652d3032 双二进制双精度: -6.14999999999999e-02不能使用空字符串作为"*"的操作数,同时执行"expr {0.5 * $double_binary_yMin}"从"set Y2
[expr {0.5 * $double_binary_yMin}]">
中调用
你从tcl::mathop::* 0.5 $yMin得到什么?
puts [tcl::mathop::* 0.5 $yMin]
不能使用空字符串作为"*">
的操作数,同时执行
"TCL::mathop::* 0.5 $yMin">
从内部
调用"放置 [tcl::mathop::* 0.5 $yMin]">
相关帖子
- 为什么Tcler建议支撑你的
expr
? - 什么意思 - 不能在 tcl- 上使用空字符串作为"*"的操作数? 如何解决
- 如何在 TCL 中去除字符串中的空格?
- 使用 TCL
从文件中读取字符串后从字符串中删除空格 - TCL 脚本
中缺少@处的操作数 - 确定 Tcl 中变量的类型
如果没有该bbox
变量的确切起点,我们只能真正推测。该值应该有效:
% set yMin -6.149999999999999e-02
-6.149999999999999e-02
% expr {0.5 * $yMin}
-0.030749999999999996
如果输入数据是普通的旧假数据,并且空字符串永远不足以支持乘法,那么所有查看expr
可能失败的方式都无济于事。(这不是Python!)我们必须备份几个步骤。
我怀疑问题是bbox
变量有时不是您期望的形状,有时具有这样的值:1.0 -6.149999999999999e-02 3.0 4.0
.在这种情况下,[lindex [lindex $bbox 0] 1]
将生成一个空字符串(因为由于语言的历史,从列表末尾索引会这样做):
% set bbox {1.0 -6.149999999999999e-02 3.0 4.0}
1.0 -6.149999999999999e-02 3.0 4.0
% puts >[lindex [lindex $bbox 0] 1]<
><
在这种情况下,仅使用lindex $bbox 1
会更好。
% puts >[lindex $bbox 1]<
>-6.149999999999999e-02<
嵌套lindex
有一个简写:
lindex $boox 0 1
但是边界框(至少当它们来自 Tk 时)通常只是四个数值的简单列表,X1Y1X2Y2
因此在它们上使用嵌套形式很可能既错误又效率低下。
这只是这里的猜想:您指出坐标来自某个模糊的来源。也许开发人员创建了一个新的对象类型,但没有正确实现转换过程。打印值时,将使用字符串表示形式。但是当你尝试乘以这个值时,它想将神秘的对象类型转换为双精度值,这似乎无法正常工作。
您一直在尝试删除空格。但由于没有空格,因此不会修改该值。但是,如果您添加空格会发生什么?例如:set yMin " $yMin"
.这应该将变量转换为纯字符串(您可以使用tcl::unsupported::representation
进行检查)。如果您随后尝试将其相乘,则将使用将字符串转换为双精度的常规 Tcl 转换过程。请注意,数字周围的空白对于expr
是完全可以接受的,所以你应该能够乘以修改后的$yMin。
这不是答案,而是带有格式的评论
% set bbox {{-4.599999999999999e-02 -6.149999999999999e-02} {8.000000000000002e-02 6.149999999999999e-02}}
{-4.599999999999999e-02 -6.149999999999999e-02} {8.000000000000002e-02 6.149999999999999e-02}
% set yMin [lindex [lindex $bbox 0] 1]
-6.149999999999999e-02
% expr {1 + $yMin}
0.9385
代码中正在发生其他更改变量值的事情。查看如何创建最小、可重现的示例