如何在IDL FOR循环中标记输出变量,以便在同一程序中进行循环外的进一步处理?

时间:2011-02-10 03:38:42

标签: idl-programming-language

我有这样的FOR循环:

FOR k = 1,216 DO  atom = G[*,0:*:(215+k)]  END

我希望能够在内存中存储每个原子的数组,比如,atom_k,然后调用这些不同的变量来执行FOR循环之外的进一步操作。 从概念上讲,我想用“k”计数器标记“atom”变量,如下所示:

FOR k = 1,216 DO  atom(k) = G[*,0:*:(215+k)]  END

当然,这不起作用,因为在这种情况下“k”不再是标签。有人知道吗?

3 个答案:

答案 0 :(得分:0)

我假设你在谈论IDTV,这是ITTVis开发的语言。 我不明白你索引G和END指令的方式,但我不使用最新版本。

尝试执行EXECUTE命令。这允许您在运行时执行语句。

FOR k = 1,216 DO status = EXECUTE('atom_'+strtrim(k,2)+' = G[,0::(215+'+strtrim(k,2)+')]') END

STRTRIM将整数转换为字符串而不会出现空白。

答案 1 :(得分:0)

看起来你正在尝试创建一个不规则的数组。你想要的是一个像列表列表的数据结构,其中子列表具有不同数量的元素。这与版本有关,但看起来8中引入的list()函数就是这样。

atoms = list()
FOR k = 1,216 DO  atoms.add, G[*,0:*:(215+k)]  END

我实际上并不认为list()是创建空列表的正确方法。无法调试它,因为我没有运行8。

答案 2 :(得分:0)

我知道有几个选项:

以下内容中,#1与您的要求最接近,但我相信#3为您提到的目标,速度以及与不同版本IDL的兼容性提供了最佳的可用性。

1)将scope_varfetch/enter关键字一起使用:

pro foo, G
    for k = 1, 216 do begin
        varname = 'atom' + strtrim(k, 1)
        (scope_varfetch(varname, level=-1, /enter)) = G[*, 0:*:(215 + k)]
    endfor
end

这会在调用例程中创建名为atom1atom216的变量,或者如果以交互方式执行,则在$MAIN$中创建变量。我认为这是你最接近你要求的。您还可以使用类似print, atom5或类似语法的语法直接从调用函数访问这些变量:

for k = 1, 216 do begin
    varname = 'atom' + strtrim(k, 1)
    print, scope_varfetch(varname)
endfor

2)使用IDL 8.0 + List对象:

atom = list(length=216)
for k = 0, 215 do atom[k] = G[*, 0:*:(216 + k)]

请注意,列表为0索引,表示第一个元素为零,而不是一个。使用atom[0]访问第一个原子,依此类推。要访问第一个原子的第一个索引,请用括号括起来,并使用另一组括号来索引:(atom[0])[0, 0]。由于IDL异常order of operations,所以括号是必要的。

3)使用指针数组:

atom = ptrarr(216)
for k = 0, 215 do atom[k] = ptr_new(G[*, 0:*:(216 + k)])

或者语法略有不同:

atom = ptrarr(216, /allocate_heap)
for k = 0, 215 do *atom[k] = ptr_new(G[*, 0:*:(216 + k)])

这是最有效和高度兼容的方式。自IDL 5.0以来,指针及相关的ptrarrptr_new函数已经出现,它们比列表,哈希值或scope_varfetch更有效。 请注意,与列表一样,这是0索引。此外,要访问这些值,您必须使用*“尊重”它们,如print, *atom[0]中打印第一个原子数组,或print, (*atom[0])[0, 0]打印第一个数组的第一个元素等等。出于与列表相同的原因,必须使用括号。使用(*atom[0])[1, 15] = new_values等语法也可以设置值。

4)使用IDL 8.0+哈希:

atoms = hash()
for k = 1, 216 do begin
    name = 'atom' + strtrim(k, 1)
    atoms[name] = G[*, 0:*:(215 + k)]
endfor

可以像atoms['atom0']一样引用它们。我不认为这可能是这种情况下的最佳选择,因为数组更有效,但如果需要使用其他字符串名称,或者数据索引稀疏,则它非常有用。

5)使用create_struct构建结构:

atoms = !null
for k = 1, 216 do begin
    tagname = 'atom' + strtrim(k, 1)
    atoms = create_struct(atoms, tagname, G[*, 0:*:(215 + k)])
endfor

非常慢,但一旦完成就相对容易理解。获取atoms.atom1之类的每个数组,并获取类似atoms.atom1[0, 0]的元素。