Arrays 自动热键在函数调用中添加到数组

Arrays 自动热键在函数调用中添加到数组,arrays,autohotkey,Arrays,Autohotkey,我知道新版本更好,但公司不允许我这么做。因此,这个问题与自动热键有关,版本为1.0.47.06 我正试图重构我的400行程序,将它们分解成函数 CaseNumberArray := "" ; The array to store all the case numbers CaseNumberArrayCount := 0 ; Helper function to load the case number into the array ReadInputFile() { Loop

我知道新版本更好,但公司不允许我这么做。因此,这个问题与自动热键有关,版本为1.0.47.06

我正试图重构我的400行程序,将它们分解成函数

CaseNumberArray := "" ; The array to store all the case numbers
CaseNumberArrayCount := 0    

; Helper function to load the case number into the array
ReadInputFile() {
    Loop, Read, U:\case.txt
    {
        global CaseNumberArrayCount
        CaseNumberArrayCount += 1 ; Increment the ArrayCount
        CaseNumberArray%CaseNumberArrayCount% := A_LoopReadLine
        current := CaseNumberArray%CaseNumberArrayCount% 
    }
}

CreateOutputHeader()
ReadInputFile()

MsgBox, There are %CaseNumberArrayCount% case(s) in the file.

Loop, %CaseNumberArrayCount% 
{
    case_number := CaseNumberArray%A_Index%
    MsgBox, %case_number%
}
代码的最后一部分是测试我是否可以检索加载到名为
casenamberaray
的数组中的案例编号,但它当前全部为空

我研究过,作者user1944441写道:

重要提示:数组不能是全局数组,并且计数器不能是全局数组 您的数组%counter%不能是全局的,其余的不重要


我尝试将全局变量放置在不同的位置,但仍然不起作用。我知道
CaseArrayCount
已正确存储,
Read循环
也在工作(当它在函数之外时)。是否可以将代码分离为一个函数

通常,
global/local
声明放在方法头的正下方,而不是放在后续代码块的某个地方。毕竟,这些声明只适用于整个函数。
您必须区分简单循环计数器变量和保存数组实际大小的变量。在您的代码中,
CaseNumberRayCount
描述了
CaseNumberRayCount
的大小,而在您所指的答案中,它是一个计数器,仅用于在数组上迭代,也可能是本地的。
但你不必使用两个“变量”。您的伪数组(可以像
casenamberray1
casenamberray2
casenamberray2
,…)有一个未使用的
casenamberray0
,为什么不在那里存储大小?
伪数组实际上是顺序编号变量的集合
global CaseNumberRay
(顺便说一句,您似乎没有尝试过)只允许访问名为
CaseNumberRay
的变量,而不允许访问
CaseNumberRay1
CaseNumberRay2
等变量。
一种解决方案是使用默认情况下可访问的每个全局变量:

; Now, CaseNumberArray0 will hold the array length,
; rendering CaseNumberArrayCount unnecessary
CaseNumberArray0 := 0 

; Helper function to load the case number into the array
ReadInputFile() {
    ; We want to access every global variable we have,
    ; beware of name conflicts within your function!
    global
    Loop, Read, test.txt
    {
        CaseNumberArray0 += 1
        CaseNumberArray%CaseNumberArray0% := A_LoopReadLine
    }
}

; Here's an alternative: Let AHK build the pseudo array!
ReadInputFileAlternative() {
    global caseAlt0
    FileRead, fileCont, test.txt
    StringSplit, caseAlt, fileCont, `n, `r
}

ReadInputFile()

out := ""
Loop, %CaseNumberArray0% 
{
    out .= CaseNumberArray%A_Index% "`n"
}

MsgBox, There are %CaseNumberArray0% case(s) in the file:`n`n%out%

; Now, let's test the alternative!
ReadInputFileAlternative()
out := ""
Loop, %caseAlt0% 
{
    out .= caseAlt%A_Index% "`n"
}

MsgBox, There are %caseAlt0% case(s) in the alternative pseudo-array:`n`n%out%
编辑:“实数组” 正如评论中所建议的那样,我会做的是:说服我的老板允许使用最新版本的AHK,然后使用真正的阵列。这有几个好处:

  • 真正的数组完全由AHK管理,这意味着插入、删除、迭代和索引等操作都可以由AHK自动完成
  • 一个实数数组驻留在一个实数变量中,这意味着您可以在函数中传递它,也可以在任何您想要的地方传递它,而不必担心当前的作用域以及是否可以首先访问它
  • 数组语法与大多数其他语言非常相似,使代码直观且易于阅读。也许它能帮助你将来处理另一种语言
  • 原始n维数组(以及通常的原始AHK对象)可以使用表示。这为您提供了一种简单的方法来(反)序列化AHK对象
  • 下面的代码片段显示了上面使用的两种方法(读取循环和拆分),但使用的是实数组。您会注意到,我们不再需要任何全局声明,因为我们现在可以在函数中声明数组,并将其传递回调用方。在我看来,函数应该是这样的:一个不会影响周围环境的“黑匣子”

    ; Method 1: Line by line
    ReadLineByLine(file) {
        out := []
        Loop, Read, % file
        {
            out.Insert(A_LoopReadLine)
        }
        return out
    }
    
    ; Method 2: StrSplit
    ReadAndSplit(file) {
        FileRead, fileCont, % file
        return StrSplit(fileCont, "`n", "`r")
    }
    
    caseNumbers := ReadLineByLine("test.txt")
    out := "ReadLineByLine() yields " caseNumbers.MaxIndex() " entries:`n`n"
    ; using the for loop
    for idx, caseNumber in caseNumbers
    {
        out .= caseNumber "`n"
    }
    MsgBox % out
    
    
    caseNumbers := ReadAndSplit("test.txt")
    out := "ReadAndSplit() yields " caseNumbers.MaxIndex() " entries:`n`n"
    ; using the normal loop
    Loop % caseNumbers.MaxIndex()
    {
        out .= caseNumbers[A_Index] "`n"
    }
    MsgBox % out
    
    MsgBox % "The second item is " caseNumbers[2]
    

    回答得很好,他们说得很有道理,我只需要回到工作电脑上,尝试一下代码。因为我的办公室使用旧版本的AHK。谢谢你的回答,我会回来的!哦,这可能是一个更好的学习机会,展示对象语法,对象实际上没有作用域,它们总是通过引用传递。