|
From: Daniel J S. <dan...@ie...> - 2007-07-01 05:44:10
|
Ethan A Merritt wrote:
> On Saturday 30 June 2007 19:49, Daniel J Sebald wrote:
>
>>Ethan A Merritt wrote:
>>
>>>On Saturday 30 June 2007 16:55, Daniel J Sebald wrote:
>>>
>>>
>>>>>But why would you want to do this?
>>>>
>>>>So that the original data is not lost. STORE_VALUE_WITH currently tosses the data.
>>>
>>>
>>>It does not.
>>>We are ignoring the log/unlog case, because it will go away.
>>
>>It currently does.
>>
>> if (VALUE<0.0) { \
>> TYPE = UNDEFINED; \
>> UNDEF_ACTION; \
>> break; \
>
>
> Only for logscale data. I said to ignore that.
>
>
>>How will it go away?
>>Are you saying that one will not be able to use mouse log/unlog scale
>>and "set logscale x", etc. unless the data file is present?
>
>
> I am saying that totally separate from this patch, we should implement
> a method of axis-scaling that is general enough to handle log scale as
> just one more scaling operation. When that is in place, input data will
> be stored as read in, and the existing special case code for log scale
> can go away.
>
>
>>I punted ... mainly because that curve-fitting code that alters the data.
>
>
> I must have missed that. Where?
It's this hunk of code. I really only looked at this closely the other day:
/* sort */
switch (this_plot->plot_smooth) {
/* sort and average, if the style requires */
case SMOOTH_UNIQUE:
case SMOOTH_FREQUENCY:
case SMOOTH_CSPLINES:
case SMOOTH_ACSPLINES:
case SMOOTH_SBEZIER:
sort_points(this_plot);
cp_implode(this_plot);
case SMOOTH_NONE:
case SMOOTH_BEZIER:
default:
break;
}
switch (this_plot->plot_smooth) {
/* create new data set by evaluation of
* interpolation routines */
case SMOOTH_FREQUENCY:
gen_interp_frequency(this_plot);
break;
case SMOOTH_CSPLINES:
case SMOOTH_ACSPLINES:
case SMOOTH_BEZIER:
case SMOOTH_SBEZIER:
gen_interp(this_plot);
case SMOOTH_NONE:
case SMOOTH_UNIQUE:
default:
break;
}
>
>>I've come to the conclusion that saving the v's and j's is preferred.
>
>
> I think I know what you mean by v[], but who are the j's?
> Anyhow, I doubt it.
while ((j = df_readline(v, max_cols)) != DF_EOF) {
The j indicates how many columns were read, upon which these big case statements are tested. Perhaps it is constant, but it may not necessarily be so. It's like another variable (with very low entropy).
>
> Counter-example 1: Consider the dumb but perfectly legal case of an input file
> with 100 columns, and the command 'plot "foo" using ($1+$2+$3+...+$100)'
> Why should we store all 100 columns, when only one value will be used?
No. v is an array of MAXDATACOLS, which is 7. So if we save those, along with j that is 8 elements, counting j as a double. The point structure has x, y, z, xlow, xhigh, ylow, yhigh, and type. Again 8 elements. We don't save 100 columns. If the user want's to get at the other columns in the data file he or she will have to issue a new "plot" command in which case "refresh" is no longer relevant. Saving a copy of the points, or a copy of the v's and j's is roughly the same.
>
> Counter-example 2: 'splot "foo" using 1:2:(system("date")) with labels'
> Not that it makes any sense to plot the date, but the point is you cannot
> assume that the value of v[3] will be the same next time you execute the plot
> command. And if it isn't, then what have you gained by saving it?
The v's and j's get recorded over if there is a new "plot".
But the labels thing is something I forgot about. This is the kind of thing that really poses a problem: multiply entry paths for data. Had a label been passed over as a series of encoded points somehow through df_readline, that'd been fine. Like the matrix data coming in from a different pathway in the plot3d.c case, patching things together like that limits flexibility. But I'm sure the "with labels" case could be handled in a similar way, I don't know.
>
>
>>The j/v's solution is actually pretty solid because of the code clean up we've done.
>>Data can only come in through df_readline() and that is where we are tapping into things.
>>On refresh, just push the code through the very beginning of the system and it
>>doesn't matter if there was curve fitting code in between.
>
>
> Are you suggesting that the curve-fitting would be re-done, and perhaps change,
> during a zoom operation? That sounds highly undesirable to me.
> And if it doesn't change, then why go back and do it again?
No, that wouldn't be desirable, perhaps. (Setting different smoothing parameters perhaps would be useful.) But the issue is the ramification on log/unlog. Say the command is one of the examples in "help acsplines" and we have logscale set:
set logscale x
sw(x,S)=1/(x*x*S)
plot 'data_file' using 1:2:(sw($3,100)) smooth acsplines
The manner in which gnuplot is set up is that data is translated to the log scale and saved. Then splines smoothing is applied to the data. Let L() represent the logarithmic translation. Let S() be the mapping resulting from splines. L() is invertible, S() isn't necessarily so, and even if it were, knowing the inversion would be difficult. So, at this point we have S(L(.)). Now, if the user unwittingly types 'l' in the plot or 'unset logscale x' at the command line then the inverse transform you've suggested, call that E() for exponentiation, then we get E(S(L(.))). In general E(S(L(.))) != S(E(L(.))), and the latter is what would happen if the user type:
unset logscale x
sw(x,S)=1/(x*x*S)
plot 'data_file' using 1:2:(sw($3,100)) smooth acsplines
This is why I'm saying be careful. Maybe they shouldn't be the same. But if people are going to use these features for scientific endeavor they need to know exactly what is happening with the data. I think there would be a little bit of confusion in that case. Whatever you do, just make sure to think this all the way through before getting to committed on the implementation.
Dan
|