I have a problem with plotting matrices with gnuplot. I am plotting one row of matrix with every option like that
plot inputfile matrix every 1:1:(4+N*M+1):100:(4+N*(M+1)):100 with linespoint
where 100 is number of row. It gave me that result:
nearly good result
I would like to get xrange from 0 to 360, but when I use something like that
plot inputfile matrix using ($1*11.25):2 every 1:1:(4+N*M+1):100:(4+N*(M+1)):100 with linespoint
it doesen't work: wrong result
What can I do with it?
You don't provide data, so I create some for the following example.
As I understand you want to plot a certain row of a matrix and adjust the x-range.
Check help matrix every.
For example, in plot FILE u 1:2:3 matrix, 1 is the column, 2 the row and 3 is the (z)-value.
And in plot FILE u 1:3 matrix every ::c:r:c:r, c is the column and r is the row (counting starts from 0).
So the example below plots the 4th row and the x-range is adjusted from 0 to 360.
Code:
### plotting a certain row while adjusting the x-range
reset session
$Data <<EOD
1 2 3 4 5 6 7
2 3 4 5 6 7 8
3 4 5 6 7 8 9
4 5 6 7 8 9 10
5 6 7 8 9 10 11
EOD
set key top left
plot $Data u ($1*60):3 matrix every :::3::3 w lp pt 7
### end of code
Result:
Related
using Gnuplot to plot 3D charts with splot and errors with zerror does not allow us to have different lines with points. Here are examples. I would like to use splot with error bars and still differentiate lines by different points. Like it is mentioned here:
The operation of with is also the same as in plot, except that the
plotting styles available to splot are limited to lines, points,
linespoints, dots, and impulses; the error-bar capabilities of plot
are not available for splot.
Is there another solution for this problem in Gnuplot?
As you note, there doesn't seem to be a direct plotting style for drawing error bars in 3D. It is possible to manipulate the input data to pseudo-draw the error bars with lines style.
Sample Script:
$inputdata <<EOD
# x y z zlow zhigh
1 1 1 0 2
2 1 2 1 3
3 1 3 2 4
4 1 4 3 5
5 1 5 4 6
1 2 5 1 7
2 2 4 1 7
3 2 3 1 7
4 2 2 1 7
5 2 1 1 7
1 3 3 1 4
2 3 3 2 5
3 3 3 3 6
4 3 3 2 5
5 3 3 1 4
EOD
# construct errorbar's line segments data
set table $first
plot $inputdata using 1:2:4:($1-0.1):4:5:0 with table
set table $second
plot $inputdata using 1:2:5:($1+0.1):4:5:0 with table
unset table
# summarize data into data block $errbars
stats $inputdata using 0 nooutput
set print $errbars
do for [i=1:STATS_records] {
print $first[i]
print $second[i]
print ""
print ""
}
set print
set xrange [0:6]
set yrange [0:4]
set key noautotitle
splot $inputdata using 1:2:3:2 with linespoints pt 7 lc variable, \
$errbars using 1:2:3:2 with lines lc variable, \
$errbars using 4:2:5:2 with lines lc variable, \
$errbars using 4:2:6:2 with lines lc variable
pause -1
It uses the line-wise data (x,y,z,zlow,zhigh) of the data points and error range as inputs to build the data to draw the error bars and whiskers. Once that's done, we can draw each part of the error bar in lines style.
Result:
Here's another solution using vector style which is actually much simpler than above script.
Sample script:
$inputdata <<EOD
# x y z zlow zhigh
1 1 1 0 2
2 1 2 1 3
3 1 3 2 4
4 1 4 3 5
5 1 5 4 6
1 2 5 1 7
2 2 4 1 7
3 2 3 1 7
4 2 2 1 7
5 2 1 1 7
1 3 3 1 4
2 3 3 2 5
3 3 3 3 6
4 3 3 2 5
5 3 3 1 4
EOD
set xrange [0:6]
set yrange [0:4]
unset key
set style arrow 3 heads size 0.05,90 lc variable
splot $inputdata using 1:2:3:2 with linespoints pt 7 lc variable, \
$inputdata using 1:2:4:(0):(0):($5-$4):2 with vectors arrowstyle 3
pause -1
Thanks.
I would like to take an average over several columns of a data set in Gnuplot. The problem is that I want to average every other column (starting from the second column of my dataset). I was thinking of using every somehow but I still don't really understand when and where to use every. To help visualise my question: my data looks something like this:
x y1 z1 y2 z2
2 0.6 0 0.6 0
1 0.7 0 0.7 1
1 0.8 2 0.8 1
1 0.9 0 0.9 0
and I would like to average y1 and y2 and plot the result by doing something like:
stats filename nooutput
plot filename u 1:sum[col = every :2::2::STATS_columns] / ((STATS_columns-1)/2)
Not sure if this is anywhere close to doable though. Also, it would be nice to have a way of finding the number of columns used without any apriori knowledge of what the data looks like. In the example I have used my knowledge of the data to know that the average is over ((STATS_columns-1)/2) number of points.
Thank you for your response
From your code I assume you want to average y1 and y2 for each row and then plot it versus x (column 1). Since you have several identical x values, there would be another average, namely an average over the columns and over all identical x values.
I modified your data to better illustrate the difference.
I guess you were asking fot the red circles. The blue triangles are basically the average of the average, i.e. the average of the red points.
Check help summation and help smooth. sum has no step size with the index.
From gnuplot help:
sum [<var> = <start> : <end>] <expression>
Code:
### average over columns and smooth
reset session
$Data <<EOD
#x y1 z1 y2 z2
1 2.0 0 4.0 0
1 2.2 0 4.2 1
1 2.9 2 4.9 1
2 2.1 0 4.1 0
2 2.3 0 4.3 0
2 2.8 0 4.8 0
3 2.2 0 4.2 0
3 2.3 0 4.3 0
3 2.7 0 4.7 0
EOD
stats $Data nooutput
set offsets 0.5,0.5,0.5,0.5
Count = (STATS_columns-1)/2
plot $Data u 1:((sum[i=1:Count] column(i*2))/Count) w p pt 7 lc rgb "red" ti "average over y1,y2 columns for each row",\
$Data u 1:((sum[i=1:Count] column(i*2))/Count) smooth unique w p pt 9 lc rgb "blue" ti "average over y1,y2 for each x"
### end of code
Result:
I am trying to create one heatmap using Gnuplot and my data file structure is looked like below:
6 5 4 3 1 0
3 2 2 0 0 1
0 0 0 0 1 0
0 0 0 0 2 3
0 0 1 2 4 3
the cell values are z values and columns represent y-axis and row are x-axes. that means the first value 6 is the z value where the y-axis is 5th position at x label zero. However, while plotting the heat map I am getting a different color which does not correlate with the z value. Also, I am getting five bins for the x-axis (which is supposed to be 6)and 4 bins (which is supposed to be 5) for the y-axis. My simple code is written below:
set pm3d map
splot 'm.txt' matrix
Please help me out of this confused situation.
Thanks.
I have the below data file which has:
1st column is the layer number.
2nd column is the X axis.
3rd column is the Y axis.
1 1999-01-19 21 0 1
1 2009-07-01 0 1 1
1 2008-08-20 2 1 1
1 2008-12-18 1 1 1
2 2004-05-12 4 1 1
2 2009-07-29 2 1 1
3 2008-08-07 0 1 1
4 2006-03-08 1 1 1
4 2004-08-31 9 1 1
4 2001-03-27 12 1 1
My questions:
1. How can I plot the above data file in 3D knowing that each layer must have different Z offset and different color?
the below must be plotted with Z=1
1 1999-01-19 21 0 1
1 2009-07-01 0 1 1
1 2008-08-20 2 1 1
1 2008-12-18 1 1 1
and the below with Z=2
2 2004-05-12 4 1 1
2 2009-07-29 2 1 1
and so on.
2.If I want to select the layer number 2, other layers must be shaded with gray and this layer must be colored with red for example, is that possible? so it's like highlighting the selected layer.
thx.
To plot the points just use
set xdata time
set timefmt '%Y-%m-%d'
set format x '%Y'
splot 'data.dat' using 2:3:1
That uses the layer number as z-value. To get something else, just specify a function for the z-value depending on the layer number:
zpos(z) = 1 + 0.5*z
splot 'data.dat' using 2:3:(zpos($1))
For the coloring use linecolor rgb variable. That allows you to specify the color in the last column. This color must be the integer representation of an rgb-tuple which is 65536*red + 256*green + blue, with red, green and blue being in the range [0:255].
The following script plots the points in layer 2 in dark red:
set xdata time
set timefmt '%Y-%m-%d'
set format x '%Y'
rgb(r,g,b) = 65536*r + 256*g + b
gray = rgb(200,200,200)
red = rgb(200,0,0)
layer = 2
set view 66,20
splot 'data.dat' using 2:3:1:($1 == layer ? red : gray) with points pt 7 linecolor rgb variable notitle
The result with 4.6.4 is:
I would like to create a heatmap with gnuplot based on a non-uniform grid, meaning that my x axis bins do not have all the same width, and I can't figure out how to do that because when I plot my data with for example "with image" I get uniformly sized boxes which do no correspond to my coordinates at all (because "image" treats the data just as matrix I guess). So I would like to find a method to get non-uniform boxes which are also positioned in the right place on the Cartesian plane.
My data look something like this:
1 1 0.2
1 2 0.8
1 3 0.1
1 4 0.2
2 1 0.7
2 2 0.2
2 3 0.3
2 4 0.1
5 1 0.2
5 2 0.4
5 3 0.1
5 4 0.9
7 1 0.3
7 2 0.2
7 3 0.9
7 4 0.6
If I run this command on Gnuplot
set xrange [1:10]
p 'mydata.dat' with image
I get an image with 16 boxes that have the same width and height (apparently I don't have enough "reputation" on Stackoverflow to post an image, otherwise I would), but ideally I would like the boxes to have different widths and be in the right place on the plane. For example the first box should range from 1 to 2, the second one from 2 to 5, the third one from 5 to 7, and the last one from 7 to 10 (which is why I wrote set xrange [1:10]).
Could anyone help me please? Thank you very much!
The easiest (maybe only viable) way is to add some dummy data points and use splot ... with pm3d. This plotting style handles heatmaps with general quadrangles.
The image plotting style plots one box (one big pixel) for each data point, while pm3d takes each data point as corner of one or more quadrangles. The color of each quadrangles is determined by the values of the corners and is adjustable with set pm3d corners2color.
So, in your case you need to expand the 4x4 matrix to a 5x5 matrix (expand to right and top), but select the lower left corner to determine the color set pm3d corners2color c1.
The changed data file is then:
1 1 0.2
1 2 0.8
1 3 0.1
1 4 0.2
1 5 0.5
2 1 0.7
2 2 0.2
2 3 0.3
2 4 0.1
2 5 0.5
5 1 0.2
5 2 0.4
5 3 0.1
5 4 0.9
5 5 0.5
7 1 0.3
7 2 0.2
7 3 0.9
7 4 0.6
7 5 0.5
10 1 0.5
10 2 0.5
10 3 0.5
10 4 0.5
10 5 0.5
To plot it use
set pm3d map corners2color c1
set autoscale fix
set ytics 1
splot 'mydata.dat' using 1:($2-0.5):3 notitle
The result with 4.6.3 is:
In general, the z-value of the dummy data points doesn't matter, but in the above script it should lay somewhere between minimum and maximum values to allow set autoscale fix to work properly on the color scale.
If you don't want to change the data file manually, you could do it with some script, but that's a different question.
Here is an alternative solution without splot ... pm3d, but with boxxyerror.
If you plot data it should go as automatic as possible and there should be no need to "invent" and manually add data.
The following solution (a little bit more complex) takes care about the widths (+/-dx) and heights (+/-dy) of the boxes according to the following principle:
if it is an "inner" box, take half the distance to the adjacent datapoint on that side
if it is an "outer" box, take half the distance to the adjacent "inner" datapoint
Here, x-distances are irregular and y-distances are regular, but y-distances could also be irregular.
Data: SO19294342.dat
1 1 0.2
1 2 0.8
1 3 0.1
1 4 0.2
2 1 0.7
2 2 0.2
2 3 0.3
2 4 0.1
5 1 0.2
5 2 0.4
5 3 0.1
5 4 0.9
7 1 0.3
7 2 0.2
7 3 0.9
7 4 0.6
Script: (works with gnuplot>=4.6.0, March 2012)
### heatmap with boxxyerror and variable box-sizes
reset
FILE = "SO/SO19294342.dat"
set style fill solid 1.0
set tics out
set size ratio -1
# extract x-positions
Xs = Ys = ''
Nx = Ny = 0
b = -1
stats FILE u (column(-1)!=b ? (Nx=Nx+1, Xs=Xs.sprintf(" %g",$1), b=column(-1)) : 0, \
column(-1)==0 ? (Ny=Ny+1, Ys=Ys.sprintf(" %g",$2)) : 0) nooutput
d(vs,n0,n1) = abs(real(word(vs,n0))-real(word(vs,n1)))/2
dn(vs,n) = (n==1 ? (n0=1,n1=2) : (n0=n,n1=n-1), -d(vs,n0,n1))
dp(vs,n) = (Ns=words(vs), n==Ns ? (n0=Ns-1,n1=Ns) : (n0=n,n1=n+1), d(vs,n0,n1))
plot FILE u 1:2:($1+dn(Xs,column(-1)+1)):($1+dp(Xs,column(-1)+1)):\
($2+dn(Ys,int(column(0))%Ny+1)):($2+dp(Ys,int(column(0))%Ny+1)):3 w boxxy palette notitle
### end of script
For gnuplot>=4.6.5 you could add :xtic(1):xtic(2) to the plot command to only show your x- and y-coordinates as x,y-ticlabels.
plot FILE u 1:2:($1+dn(Xs,column(-1)+1)):($1+dp(Xs,column(-1)+1)):\
($2+dn(Ys,int(column(0))%Ny+1)):($2+dp(Ys,int(column(0))%Ny+1)):3:\
xtic(1):ytic(2) w boxxy palette notitle
And for gnuplot>=5.0.0 you could add noextend to the ranges to avoid white areas on the sides:
set xrange[:] noextend
set yrange[:] noextend
Result: (created with gnuplot 4.6.0)