Tcl / Tk: область видимости переменных для функции внутри функции - PullRequest
0 голосов
/ 11 ноября 2018

Я теряюсь из-за переменных в Tcl. У меня есть два прока, которые я написал и сохранил в файле, который я хочу вызвать в другом скрипте, который я пишу. В моем исходном файле (который я назову bar.tcl) я использую upvar для определения группы переменных в начале моего файла, которые я планирую вызывать в рамках процедур, которые я определил в bar.tcl который я назову bar1 и bar2

Я хочу вызвать функции из bar.tcl из моего кода в foo.tcl. Мои функции работают нормально, если я просто взаимодействую с bar.tcl в tclsh, но как только я вызываю bar1 или bar2 из функции в foo.tcl, я получаю ошибку can't read "alpha": no such variable

Кажется, я использую upvar неправильно. Это даже правильный инструмент для работы? Что я могу сделать, чтобы достичь следующего?

  1. определяет группу переменных в начале bar.tcl, которые я хочу использовать в обоих процессах bar1 и bar2, и
  2. вызов bar1 и bar2 из процедур, определенных в foo.tcl

Вот мой код в foo.tcl:

# foo.tcl
source bar.tcl

proc foo {fooValues} {
    foreach fooValue $fooValues {
        set myNewValue [bar1 $fooValue]
        return $myNewValue
    }
}

set myOldValues {5 10 15 20 25}
foo myOldValues

А вот мой код в bar.tcl:

set a apples
set b bananas
set c cherries
set d dates

proc bar1 {bar} {
    upvar a alpha
    upvar b bravo
    upvar c charlie
    upvar d delta

    set myReturnValue "$bar $alpha $bravo $charlie $delta"
    return $myReturnValue
}

proc bar2 {bar} {
    upvar a alpha
    upvar b bravo
    upvar c charlie
    upvar d delta

    set myReturnValue "$alpha $bravo $charlie $delta $bar"
    return $myReturnValue
}

1 Ответ

0 голосов
/ 11 ноября 2018

Когда bar1, bar2, ... вызываются из foo, их вызовы upvar будут пытаться соединиться с любыми локальными переменными proc выполненного foo proc. Это связано с тем, что upvar без уровня по умолчанию имеет значение upvar 1, которое обозначает вызывающего процесса (т. Е. foo). Однако целевые переменные в bar.tcl находятся в глобальном пространстве имен, а не в foo. Следовательно, нет переменных, связанных с alpha, bravo.

Переписать ваши upvar вхождения как upvar #0 ..., с #0, указывающим глобальное пространство имен верхнего уровня, например ::

upvar "#0" a alpha

Это эквивалентно использованию global a по модулю псевдонима переменной (alpha).

...