2

I have a bunch of time-dependent data, non-decreasing and right-continuous, always with come category involved, that can be repeated. I am looking for a sort of a variable width-bar chart, or cascade chart, flipped on it's side, from the right. For example,

set term postscript eps enhanced
set output "so.eps"
$Data <<EOD
# date  source  reg sic pic total
2000-07-25  2000glider  C-FJSN  8   0   216
2000-07-28  2000glider  C-FJSN  10  0   226
2000-07-28  2000glider  C-FJSN  11  0   237
2000-07-28  2000glider  C-GCLB  4   0   241
2000-07-29  2000glider  C-GCLY  3   0   244
2000-07-29  2000glider  C-GCLY  2   0   246
2000-07-29  2000glider  C-GCLY  17  0   263
2000-07-30  2000glider  C-GCLB  15  0   278
2000-07-30  2000glider  C-GCLB  0   13  291
2000-07-30  2000glider  C-GCLK  11  0   302
2000-07-30  2000glider  C-FJSN  0   16  318
2000-07-30  2000glider  C-GCLB  0   10  328
2000-08-02  2000glider  C-GQRT  0   13  341
2000-08-04  2000glider  C-GCLY  0   11  352
2000-08-05  2000glider  C-GCLB  12  0   364
2000-08-05  2000glider  C-GCLB  0   12  376
2000-08-06  2000glider  C-GCLB  0   11  387
2000-08-07  2000glider  C-GFMB  0   12  399
2000-08-07  2000glider  C-GCMB  0   11  410
2000-08-08  2000glider  C-GCLK  0   12  422
2000-08-09  2000glider  C-GCLB  14  0   436
2000-08-09  2000glider  C-GCLB  0   9   445
2000-08-10  2000glider  C-GCLL  0   10  455
EOD
set monochrome
set xdata time
set timefmt "%Y-%m-%d"
set xtics format "%Y-%m-%d" rotate by -30
set ylabel "hours"
set grid
unset key
unset border
plot $Data using 1:($6/60) with fillsteps lw 2, \
 $Data using 1:($6/60):3 with labels

Which gives,

Output of the script above.

I'm trying to create like a cumulative distribution function, where hours, in this case, are added. I want the line to go to zero on the left and the maximum value on the right. The labels, instead of printing, should be in the key and mapped to the data, grouped with other consecutive data, from the right. Is there such a plot, and how to I create it?

I have full control over the input, so I was thinking maybe an inverse-transform and rotate would be easier?

Neil
  • 1,767
  • 2
  • 16
  • 22

1 Answers1

2

Not sure if I fully understood all your points correctly. Maybe the following script might bring you closer to what you want.

Update:

If you want color bars for intervals then you could use the plotting style with boxxyerror (check help boxxy).

  • with boxxy requires either 4 or 6 columns. 4 columns would be (x):(y):(dx):(dy) for a box centered at x,y with +/-dx and +/-dy.

  • sum up your durations which are either in column 4 or 5 in the variable total. No need for column 6.

  • the difference dx=43200 (i.e. half a day in seconds)

There are different ways of plottings steps.

Script:

### cumulative plot with color code
reset session

$Data <<EOD
# date  source  reg sic pic total
2000-07-25  2000glider  C-FJSN  8   0   216
2000-07-28  2000glider  C-FJSN  10  0   226
2000-07-28  2000glider  C-FJSN  11  0   237
2000-07-28  2000glider  C-GCLB  4   0   241
2000-07-29  2000glider  C-GCLY  3   0   244
2000-07-29  2000glider  C-GCLY  2   0   246
2000-07-29  2000glider  C-GCLY  17  0   263
2000-07-30  2000glider  C-GCLB  15  0   278
2000-07-30  2000glider  C-GCLB  0   13  291
2000-07-30  2000glider  C-GCLK  11  0   302
2000-07-30  2000glider  C-FJSN  0   16  318
2000-07-30  2000glider  C-GCLB  0   10  328
2000-08-02  2000glider  C-GQRT  0   13  341
2000-08-04  2000glider  C-GCLY  0   11  352
2000-08-05  2000glider  C-GCLB  12  0   364
2000-08-05  2000glider  C-GCLB  0   12  376
2000-08-06  2000glider  C-GCLB  0   11  387
2000-08-07  2000glider  C-GFMB  0   12  399
2000-08-07  2000glider  C-GCMB  0   11  410
2000-08-08  2000glider  C-GCLK  0   12  422
2000-08-09  2000glider  C-GCLB  14  0   436
2000-08-09  2000glider  C-GCLB  0   9   445
2000-08-10  2000glider  C-GCLL  0   10  455
EOD

# get a unique list from datablock
addToList(list,col) = list.( strstrt(list,'"'.strcol(col).'"') > 0 ? \
                      '' : ' "'.strcol(col).'"')
Uniqs = ''
stats $Data u (Uniqs=addToList(Uniqs,3)) nooutput
Uniq(i)     = word(Uniqs,i)
getIndex(s) = sum [_i=1:words(Uniqs)] s eq word(Uniqs,_i) ? _i : 0

myTimeFmt = "%Y-%m-%d"

set format x myTimeFmt timedate
set xtics format myTimeFmt rotate by -30
set ylabel "hours"
set format y "%tH:%tM" timedate
set grid
set key out reverse Left noautotitle
set style fill solid 0.5

plot  total=0 $Data u (timecolumn(1,myTimeFmt)):(dy=($4+$5)*60,total=total+dy) w steps lc "black" dt 3, \
      total=0 ''    u (timecolumn(1,myTimeFmt)):(dy=($4+$5)*60,total=total+dy,total-dy/2.): \
         (43200):(dy/2.):(getIndex(strcol(3))) w boxxy lc var, \
     for [i=1:words(Uniqs)] keyentry w boxxy lc i ti Uniq(i)
### end of script

Result:

enter image description here

theozh
  • 22,244
  • 5
  • 28
  • 72
  • That's amazing; I think it's exactly what the key should be. Ideally, instead of just a point, _eg_, on the bottom I'd like a horizontal bar that encompasses the first three `C-FJSN`. On the last upper `C-GCLL`, we see the problem I've run into where either one side is broken or the other, because it's an interval not a point. Any suggestions? – Neil Feb 16 '23 at 04:01
  • @Neil you could use plotting style `with boxxy`. See modified answer... – theozh Feb 16 '23 at 06:37
  • 1
    @Neil, only now, I noticed that the duration in minutes of each entry is actually either in column 4 or 5. So the plotting command could probably be simplified somewhat, because gnuplot could easily sum up these values instead of calculating the differences from the 6th column. – theozh Feb 16 '23 at 07:11
  • Great answer; looks so much more readable! Yes, I had trouble with cumulative together with steps and fill so I just added a column; that depends on the other columns. – Neil Feb 16 '23 at 07:20
  • 1
    @Neil oops, then the positions and colors of the boxes were wrong in the previous answer. I will update the answer. – theozh Feb 16 '23 at 07:57
  • Yes, that is better. I love that sort-of ellipsis on the graph joining two squares; very nice feature. – Neil Feb 16 '23 at 08:15