ASE Home Page Products Download Purchase Support About ASE
ChartDirector Support
Forum HomeForum Home   SearchSearch

Message ListMessage List     Post MessagePost Message

  $perlchartdir + aggregate()
Posted by Tobias Reu on Oct-23-2013 23:20
Hi Peter,

there seems to be a problem with aggregating data-series with NoValue. Here is my test-script:

use perlchartdir;
  my @dateArray = (1,2,3,4,5,6,7,8,9,10,11,12);
  my @closeArray = (1,2,3,4,5,6,7,8,9,10,$perlchartdir::NoValue,$perlchartdir::NoValue);
  use Data::Dumper;
  print STDERR Dumper(\\@closeArray)."\\n";

  my $i = 0;
  foreach my $v (@closeArray) {
    if ($v == $perlchartdir::NoValue) {
      print STDERR "NoValue on index-position ".$i."\\n";
    }
    $i++;
  }

  my $aggregator = new ArrayMath(\\@dateArray)->selectRegularSpacing(2);
  @closeArray    = @{$aggregator->aggregate(\\@closeArray, $perlchartdir::AggregateLast)};
  print STDERR Dumper(\\@closeArray)."\\n";

  $i = 0;
  foreach my $v (@closeArray) {
    if ($v == $perlchartdir::NoValue) {
      print STDERR "NoValue on index-position ".$i."\\n";
    }
    $i++;
  }

OUTPUT
$VAR1 = [
          1,
          2,
          3,
          4,
          5,
          6,
          7,
          8,
          9,
          10,
          '1,7e+308',
          '1,7e+308'
        ];
NoValue on index-position 10
NoValue on index-position 11

$VAR1 = [
          '2',
          '4',
          '6',
          '8',
          '10',
          '1,7e+308'
        ];

Before aggregating the data, i can recognize the NoValue by comparing, after aggregation it is not possible (missing output "NoValue on index-position 5"). It works fine in an older version!

Regards
Tobi

  Re: $perlchartdir + aggregate()
Posted by Peter Kwan on Oct-24-2013 02:58
Hi Tobias,

This is due to a special "feature" in Perl, in that Perl treats the 1.7E+308 in a way that is not equivalent to the 1.7E+308 in C++. (This occurs in many other floating point numbers as well.)

It is not possible to represent many numbers in decimal notation. For example, you cannot write 1/3 in decimal (it would like infinite number of decimal points). In practice, you may have to round it to a finite number of decimal place.

The same applies to binary numbers. It happens it is not possible to represent 1.7E+308 in binary, but the method Perl rounds it may be different from gcc (the C compiler). (The gcc method is the most commonly used method as the entire Linux OS is built using gcc.)
It depends on the Perl version, compilation method, OS version, hardware type, and is hard to predict. Sometimes it matches with gcc and sometimes it doesn't.

In our own code, if we need to compare a NoValue coming from ChartDirector to $perlchartdir::NoValue, we would use the following method (eg. see Line 2100 in FinanceChart.pm):

if (abs($data->[$i] / $perlchartdir::NoValue - 1) > 1e-005) {

......

}

Basically, it compares if the ratio of the two values are close enough to 1 that they should be considered as equivalent.

Hope this can help.

Regards
Peter Kwan

  Re: $perlchartdir + aggregate()
Posted by Tobias Reu on Oct-24-2013 23:29
That works fine. Thank you for this resolution!