Хорошо, я продолжаю возвращаться к этому - так что я думаю, что мне нужно было следующее разъяснение:
Учитывая, что gnuplot
, ну, ну, отображает наборы данных как 2D-графики - это данность, с которой как-то имеет дело2D структуры или массивы.Вот почему кто-то из C, Perl, Python и т. Д., Естественно, подумает, что можно каким-то образом проиндексировать набор данных и получить значение в заданной позиции строки и столбца;скажем, что-то вроде следующего псевдокода:
my_val = "inline.dat"[1][2] # get value in 1st row and 2nd column
Или, альтернативно, псевдокод:
my_dataset = parse_dataset("inline.dat")
my_val = get_value(my_dataset, 1, 2)
И я потратилВ поисках чего-то подобного в gnuplot
я потратил много времени и ничего подобного не мог найти (прямой доступ к значениям набора данных через индекс строк и столбцов).Кажется, что only вещь, которую можно сделать, это plot
набор данных - и, возможно, доступ к значениям там через функцию, вызванную в части using
.
Это означает, что если я хочу найти некоторые значения набора данных из gnuplot
, у меня есть для итерации по набору данных путем вызова plot
- даже если мне нужны именно эти значения дляпостроить правильное plot
выражение :)
И мне это как-то не нравится, думая, что первое plot
может каким-то образом испортить второе :)
Однако, как находит максимальное значение в наборе данных и вычитает изсюжет - comp.graphics.apps.gnuplot |Группы Google указывают, что один может plot
в файл, также stdout
или /dev/null
, и получает простую таблицу в формате ASCII - так что, по крайней мере, я могу перенаправить первый вызов втаким образом, так что это не мешает действительному графическому терминалу второго вызова plot
.
Итак, ниже приведен еще один пример кода, где первый элемент первого столбца в наборе данных "inline.dat
" извлекается с помощью:
# print and get (in _drcv) first value of first data column:
eval print_dataset_row_column("inline.dat",0,1)
# must "copy" the "return" value manually:
first = _drcv
... так что график можетбыть смещенным на first
непосредственно в вызове plot
.
Обратите внимание, что print_dataset_row_column
вызывает plot
(перенаправляется через set table
на /dev/null
) - и, таким образом, каждый каждый раз, когда вы вызываете его для получения одиночное значение , оно будет вызывать итерацию по всему набору данных Весь !Так что если вам нужен первый элемент и последний элемент (и, возможно, другие вещи, такие как некоторая базовая статистика с помощью gnuplot ), вероятно, лучше переписать print_dataset_row_column
, чтобы он извлекал все эти данные за один раз.
Также потребуется перезапись print_dataset_row_column
, если вы используете некоторые специальные форматы в наборе данных и в строке using
.Обратите внимание, что в этом примере третий столбец является строкой, которая по умолчанию не принимается в качестве столбца данных графика;и как таковые, вызовы функций print_dataset_*
не будут выполнены, если им придется иметь дело с этим (см. также gnuplot plot из строки ).
Так вотпример кода - давайте назовем его test.gp
:
# generate data
system "cat > ./inline.dat <<EOF\n\
10.0 1 a 2\n\
10.2 2 b 2\n\
10.4 3 a 2\n\
10.6 4 b 2\n\
10.8 5 c 7\n\
11.0 5 c 7\n\
EOF\n"
### "dry-run" functions:
# iterate through dataset by calling
# `plot`, redirected to file output (via `set table`)
#
# note: eval (not print) cannot be inside a user-defined function:
# a(b) = eval('c=3') ; print a(4) ==> "undefined function: eval"
# nor you can make multistatement functions with semicolon:
# f(x) = (2*x ; x=x+2) ==> ')' expected (at ';')
#
# so these functions are defined as strings - and called through eval
#
# through a single column spec in `using`:
# (`plot` prints table to stdout)
#
print_dataset_column(filename,col) = "set table '/dev/stdout' ;\
plot '".filename."' using ".col." ;\
unset table"
#
# through two column spec in `using`:
# (`plot` prints table to stdout)
#
print_dataset_twocolumn(filename,colA,colB) = "set table '/dev/stdout' ;\
plot '".filename."' using ".colA.":".colB." ;\
unset table"
#
# print value of row:column in dataset, saving it as _drcv variable
#
# init variable
#
_drcv = 0
#
# create _drc helper function; note assign and "return" in
# true branch of ternary clause
#
_drc(ri, colval, col) = (ri == _row) ? _drcv = colval : colval
#
# define the callable function:
#
print_dataset_row_column(filename,row,col) = "_row = ".row." ;\
set table '/dev/null' ;\
plot '".filename."' using (_drc($0, $".col.", ".col.")) ;\
unset table ;\
print '".filename."[r:".row.",c:".col."] = ',_drcv"
#
#
### end dry run functions
#
# test print_dataset_* functions:
#
eval print_dataset_column("inline.dat",0)
eval print_dataset_twocolumn("inline.dat",0,0)
# string column - cannot directly:
# set table '/dev/stdout' ;plot 'inline.dat' using 3 ;unset table
# ^
# line 69: warning: Skipping data file with no valid points
# line 69: x range is invalid
#~ eval print_dataset_column("inline.dat",3)
eval print_dataset_column("inline.dat",1)
eval print_dataset_twocolumn("inline.dat",1,2)
eval print_dataset_row_column("inline.dat",4,1)
eval print_dataset_row_column("inline.dat",4,2)
# will fail - 3 is string column
# line 82: warning: Skipping data file with no valid points
# line 82: x range is invalid
#~ eval print_dataset_row_column("inline.dat",4,3)
#
# do a plot offset by first element position
#
# print and get (in _drcv) first value of first data column:
eval print_dataset_row_column("inline.dat",0,1)
# must "copy" the "return" value manually:
first = _drcv
# ranges
set yrange [0:8]
set xrange [0:11.5]
# plot finally:
plot "inline.dat" using ($1-first):2 with impulses linewidth 2
Когда этот скрипт вызывается, набор данных в OP строится смещением, начиная с 0 - и в терминале выводится следующее (первые несколькораспечатки таблицы - это фактический вывод от plot
, перенаправленный через set table
до stdout
):
gnuplot> load './test.gp'
# Curve 0 of 1, 6 points
# Curve title: "'inline.dat' using 0"
# x y type
0 0 i
1 1 i
2 2 i
3 3 i
4 4 i
5 5 i
# Curve 0 of 1, 6 points
# Curve title: "'inline.dat' using 0:0"
# x y type
0 0 i
1 1 i
2 2 i
3 3 i
4 4 i
5 5 i
# Curve 0 of 1, 6 points
# Curve title: "'inline.dat' using 1"
# x y type
0 10 i
1 10.2 i
2 10.4 i
3 10.6 i
4 10.8 i
5 11 i
# Curve 0 of 1, 6 points
# Curve title: "'inline.dat' using 1:2"
# x y type
10 1 i
10.2 2 i
10.4 3 i
10.6 4 i
10.8 5 i
11 5 i
inline.dat[r:4,c:1] = 10.8
inline.dat[r:4,c:2] = 5.0
inline.dat[r:0,c:1] = 10.0