Страница 3 из 4

Re: Значение переменной вывести в название другой переменной.

Добавлено: 03 сен 2017, 23:01
podarok66
Я могу только предположить, что в вашем варианте запроса получаемый ответ выдается не в виде числа,а какого-то единого значения. Потому как если взять длину значения в вашем случае, будет единица.

Код: Выделить всё

:global rxbyte [/interface ethernet get WAN rx-bytes];
:put $rxbyte;
17 575 300 924
:put [:len $rxbyte]
1

В моём варианте будет именно числовое значение, и его длина будет совсем не такой:

Код: Выделить всё

:global rxbyte [/interface get [find name=WAN] rx-byte]   
 :put $rxbyte                                           
17575300924
:put [:len $rxbyte]
11

А в целом, примите это как данность и не парьтесь. Я сам не знаю, почему всё именно так, а не иначе :-)

Re: Значение переменной вывести в название другой переменной.

Добавлено: 03 сен 2017, 23:43
enternight
еще раз выражаю вам огромную благодарность
данность принята на вооружение :ps_ih:

Re: Значение переменной вывести в название другой переменной.

Добавлено: 04 сен 2017, 08:59
podarok66
Да не за что, собственно. Вы спрашивайте, если будет надобность. В кои-то веки посетитель подкинул интересный вопрос, я хоть покопался немного для своего удовольствия.

Re: Значение переменной вывести в название другой переменной.

Добавлено: 18 сен 2019, 11:48
Sertik
А на первоначальный вопрос не ответили так и ...

Допустим есть переменная $key значение которой меняется ... (пусть хоть от 1 до 10 или буквенные различные)
Следующей командой создаем переменную с именем lte$key

:parse [:execute ":global lte$key ({})"]

Нужная переменная в окружении создается, это видно в environment, но как ей оперировать - то есть имя ее итоговое то мы так и не знаем !
Как ей например присваивать значения ?

Re: Значение переменной вывести в название другой переменной.

Добавлено: 18 сен 2019, 12:51
Sertik
более того, если зная $key попытаться получить :type переменной, составленной из lte + $key (допустим lte1) то получаем nothing !
То есть в окружении переменная создалась, но реально ее нет. Не помогает и предварительное преобразования $key в строковое значение.
Очень странно.

Такая задача нужна была бы ну например - Вы ищете скриптом что-либо не зная заранее результат этих поисков.
Я, например, пытаюсь искать lte-интерфейсы на Микротике. Если я нахожу, то хочу создать массив, имеющий имя равное имени lte-интерфейса, а потом загнать в него параметры из lte info

Re: Значение переменной вывести в название другой переменной.

Добавлено: 18 сен 2019, 13:38
Sertik
Теперь, кажется, становится понятным в чем дело ... Дело в том, что в самом скрипте, где выполняется
:execute ":global lte$key ({})" создаваемая переменная не объявляется ! То есть, она в окружении создается, то скрипту остаётся не известной.
Это проверяется просто. Допустим $key это "1"

Тогда:
:execute ":global lte$key ({})"
:set $lte1 "test"
выполнено не будет, т.к. $lte1 не объявлена и не известна, а

:execute ":global lte$key ({})"
:global lte1
:set $lte1 "test"

работает.

Как тут быть не понятно.

Re: Значение переменной вывести в название другой переменной.

Добавлено: 18 сен 2019, 19:26
podarok66
Таблица из вложения не поможет? Там вроде как всё очень скрупулёзно человек просмотрел. Если что, по названию файла поиск в гугле должен привести к статье на хабре, где и позаимствована табличка...

Re: Значение переменной вывести в название другой переменной.

Добавлено: 19 сен 2019, 09:50
Sertik
За табличку спасибо. Я этот текст и исследование переменных знаю.
Дело не в этом, кажется.

Дело в том что если делаем из скрипта :execute ":global $Var" или :parse [:execute ":global $Var"] (как предложил когда то vqd) переменная с именем равным значению переменной $Var в окружении действительно создается !, но скрипт, который это делает всё равно "ничего о ней не знает", т.к. она остается для него как бы не объявленной и оперировать ей нельзя !
А сделать прямо :global $Var из скрипта естественно нельзя - "синтаксическая ошибка", т.к. "$" автоматически означает "значение" переменной.

Вот и получается, что создать переменную с именем равным значению переменной из скрипта как бы можно (см. абзац 1), а пользоваться ей нельзя пока её не объявить снова через :global, но точно указав её имя. Можете попробовать сами. То есть :execute переменную создает как бы именно в "фоновом" режиме, в обход какой-то важной подпрограммы РОС, которая объявляет её !

Это ограничение, вероятно, скриптового языка РОС. Не знаю с какой целью это сделано, вероятно цель была ...
Если кто опровергнет и найдет способ создать переменную с именем равным значению другой переменной, но так, чтобы она стала доступна из скрипта - буду только рад ...

Интересно, что переменные созданные путем :execute ":global $Var скрипту не известны, а консоли - да, можно попробовать :log info $Var и :put $Var. В первом случае получим етественно ничего, а :put значение выводит, что логично - созданная в "фоновом" режиме переменная системе известна, а скрипту нет, т.к. в нем не объявлена.

Вот тут viewtopic.php?f=14&t=9180 похожая тема уже обсуждалась, но рассматривались другие типы создания переменных ... (не с именем равным значению), тоже может быть полезно.

Написал с горя в support mikrotik, поглядим что ответят ... А вот и ответ прилетел:


Hello,

RouterOS scripting does not support declaring variables which names are taken from another variables value.
Regarding your question, variable is not declared in current scope, that is why you cannot get its value until ;global varname; is added to the script.

Best regards,
Maris B.

Что, собственно, и следовало ожидать. Так, что извращения вида :parse [:execute ":global $Var"] ,увы, бессмыссленны.

Вопрос исследован и закрыт.

Re: Значение переменной вывести в название другой переменной.

Добавлено: 13 фев 2024, 21:55
deniseik
Нашел способ!

Запись переменной:

Код: Выделить всё

local x "X"
local y "Y"
execute "global $x $y"
Чтение переменной:

Код: Выделить всё

local z
foreach i in=[sys/scr/env find] do {
	if ($x=[sys/scr/env get $i name]) do {
		set z [sys/scr/env get $i value]
	}
}

Re: Значение переменной вывести в название другой переменной.

Добавлено: 14 фев 2024, 14:17
Sertik
Похвально, но:

1. Надо проверить Ваше решение
2. Из Вашего решения получается, чтобы работать с одной переменной нужно перебрать все переменные в окружении, что не оправдано затратно по ресурсам процессора
3. Если искать решение - оно должно быть другим ... (без цикла перебора всех переменных ...)
4. И, по крайней мере уж как-то так (систаксис не проверял) .... чтобы хоть понятно было программисту откуда ноги растут ...
5. Сокращать команды ROS в скриптах (если это ещё не продакшен :-):) не стоит, вне зависимости от синтаксиса версии (6 или 7 не важно), так как потом сами запутаетесь и вспоминать будете что и как написали когда-то ...

Код: Выделить всё

local z
/system script environment

:foreach item in=[:find] do {
         if ($x=[:get $item name]) do={set z [:get $item value]
     }
}