1

I am trying to write an Octave C++ .oct function that uses the linasm-1.13 library but I cannot seem to get even basic loading of tzdata from /usr/share/zoneinfo/ to work. My simple test function so far is

#include <octave/oct.h>
#include <Time.h> // the linasm-1.13 library

DEFUN_DLD ( tz, args, nargout,
"-*- texinfo -*-\n\
@deftypefn {Function File} {} tz (@var{YYYYMMDDHHMMSS})\n\
\n\
@end deftypefn" )

{
octave_value_list retval_list ;
unsigned int tz ;

const char *ny_time = "/usr/share/zoneinfo/America/New_York" ; 

tz = Time::LoadTimeZone( ny_time ) ;

return retval_list ;

which, on compiling with mkoctfile, gives this error

>> mkoctfile tz.cc
tz.cc: In function ‘octave_value_list Ftz(const octave_value_list&, int)’:
tz.cc:24:34: error: cannot call member function ‘unsigned int  Time::LoadTimeZone(const char*)’ without object
tz = Time::LoadTimeZone( ny_time ) ;
                              ^
warning: mkoctfile: building exited with failure status

My understanding of this is that ny_time is not an object that is recognised, but I have tried casting ny_time as a string literal as detailed in this accepted SO answer.

I am doing things this way because the input for LoadTimeZone according to the linasm page should be a "path to tzfile, which describes required time zone." Where am I going wrong?

babelproofreader
  • 530
  • 1
  • 6
  • 20
  • From the error message it appears you need to construct a `Time` object first and then call `LoadTimeZone` on that object. So, you might also need to provide an Octave wrapper around the `Time` class and then require the Octave code to provide that. – Daniel Schepler Nov 03 '17 at 22:44
  • Incidentally, in most cases I prefer using Swig over manually writing bindings, as Swig takes care of a lot of the tedious details for you (and it does support generating Octave bindings). – Daniel Schepler Nov 03 '17 at 22:45
  • If you are using C++11 or later, here is an alternative timezone library you might consider: https://howardhinnant.github.io/date/tz.html It has excellent documentation and support. – Howard Hinnant Nov 04 '17 at 15:14
  • Thread on the help mailinglist http://octave.1599824.n4.nabble.com/Conversion-from-UTC-to-specified-Timezone-td4685549.html – Andy Nov 09 '17 at 17:32

1 Answers1

0

I think you have to #include "source.cc" files also, not just the #include "header.h" files. In your case, I guess you should add: #include "Time.cc" or something like that. I don't know why but this worked for me when working with Rafat's Hussain wavemin library, but I had only 4 files, it must be incredibly tedious with lots of files.

This is what I did (it's a modified version of the test code provided by Rafat with his library).

#include "wavemin.h"
#include "waveaux.h"
#include "wavemin.cc"
#include "waveaux.cc"
#include <octave/oct.h>

double ensayo();
double absmax(double *array, int N);

DEFUN_DLD(helloctave2, argv, , "Usage: hello()"){   

    wave_object obj;
    wt_object wt;
    double *inp, *out, *diff;
    int N, i, J;
    char *name = "db4";
    obj = wave_init(name);// Initialize the wavelet
    N = 14;  //Length of Signal
    inp = (double*)malloc(sizeof(double)* N); //Input signal
    out = (double*)malloc(sizeof(double)* N);
    diff = (double*)malloc(sizeof(double)* N);
    //wmean = mean(temp, N);
    for (i = 0; i < N; ++i) {
        inp[i] = i;
    }
    J = 1; //Decomposition Levels
    wt = wt_init(obj, "dwt", N, J);// Initialize the wavelet transform object
    setDWTExtension(wt, "sym");// Options are "per" and "sym". Symmetric is the default option
    setWTConv(wt, "direct");
    dwt(wt, inp);// Perform DWT
    //DWT output can be accessed using wt->output vector. Use wt_summary to find out how to extract appx and detail coefficients
    for (i = 0; i < wt->outlength; ++i) {
    octave_stdout << wt->output[i];
    octave_stdout << "\n";
    }

    idwt(wt, out);// Perform IDWT (if needed)
    // Test Reconstruction
    for (i = 0; i < wt->siglength; ++i) {
        diff[i] = out[i] - inp[i];
    }

  octave_stdout << absmax(diff, wt->siglength);
  octave_stdout << "\n"; 

  octave_value_list retval;             

  return retval;                            
}       

double
absmax(double *array, int N) {
    double max;
    int i;
    max = 0.0;
    for (i = 0; i < N; ++i) {
        if (fabs(array[i]) >= max) {
            max = fabs(array[i]);
        }
    }
    return max;
}