The R Project SVN R-packages

Rev

Rev 3432 | Rev 3446 | Go to most recent revision | Show entire file | Regard whitespace | Details | Blame | Last modification | View Log | RSS feed

Rev 3432 Rev 3434
Line 429... Line 429...
429
 * from sdf_data". */
429
 * from sdf_data". */
430
static long double g_accumulator = 0.0; /* accumulator var for cumsum, cumprod, etc. */
430
static long double g_accumulator = 0.0; /* accumulator var for cumsum, cumprod, etc. */
431
static int g_start = 0;            /* flag for start of cummulation */
431
static int g_start = 0;            /* flag for start of cummulation */
432
static int g_narm = 0;             /* for Summary group */
432
static int g_narm = 0;             /* for Summary group */
433
 
433
 
434
SEXP sdf_do_variable_math(SEXP func, SEXP vector, SEXP extra_args, SEXP _nargs) {
434
SEXP sdf_do_variable_math(SEXP func, SEXP vector, SEXP other_args) {
435
    char *iname, *iname_src, *varname_src, *funcname;
435
    char *iname, *iname_src, *varname_src, *funcname;
436
    int namelen, res, nargs;
436
    int namelen, res;
437
    sqlite3_stmt *stmt;
437
    sqlite3_stmt *stmt;
438
 
438
 
439
    /* get data from arguments (function name and sqlite.vector stuffs) */
439
    /* get data from arguments (function name and sqlite.vector stuffs) */
440
    funcname = CHAR_ELT(func, 0);
440
    funcname = CHAR_ELT(func, 0);
441
    iname_src = SDF_INAME(vector);
441
    iname_src = SDF_INAME(vector);
442
    varname_src = SVEC_VARNAME(vector);
442
    varname_src = SVEC_VARNAME(vector);
443
    nargs = INTEGER(_nargs)[0];
-
 
444
 
443
 
445
    if (!USE_SDF1(iname_src, TRUE, TRUE)) return R_NilValue;
444
    if (!USE_SDF1(iname_src, TRUE, TRUE)) return R_NilValue;
446
 
445
 
447
    /* check nargs */
-
 
448
    if (nargs > 2) {
-
 
449
        Rprintf("Error: Don't know how to handle Math functions w/ more than 2 args\n");
-
 
450
        return R_NilValue;
-
 
451
    }
-
 
452
 
-
 
453
    /* create a new sdf, with 1 column named V1 */
446
    /* create a new sdf, with 1 column named V1 */
454
    iname = _create_svector1(R_NilValue, "double", &namelen, TRUE);
447
    iname = _create_svector1(R_NilValue, "double", &namelen, TRUE);
455
 
448
 
456
    /* insert into <newsdf>.col, row.names select func(col), rownames */
449
    /* insert into <newsdf>.col, row.names select func(col), rownames */
-
 
450
    if (strcmp(funcname, "round") == 0 || strcmp(funcname, "signif") == 0) {
-
 
451
        double digits = REAL(_getListElement(other_args, "digits"))[0];
-
 
452
        sprintf(g_sql_buf[0], "insert into [%s].sdf_data([row name], V1) "
-
 
453
                "select [row name], %s([%s],?) from [%s].sdf_data", iname, funcname,
-
 
454
                varname_src, iname_src);
-
 
455
        res = sqlite3_prepare(g_workspace, g_sql_buf[0], -1, &stmt, 0); 
-
 
456
        if (_sqlite_error(res)) goto vecmath_prepare_error;
-
 
457
        res = sqlite3_bind_double(stmt, 1, digits);
-
 
458
    } else if (strcmp(funcname, "log") == 0) {
-
 
459
        double base = REAL(_getListElement(other_args, "base"))[0];
-
 
460
        sprintf(g_sql_buf[0], "insert into [%s].sdf_data([row name], V1) "
-
 
461
                "select [row name], %s([%s],?) from [%s].sdf_data", iname, funcname,
-
 
462
                varname_src, iname_src);
-
 
463
        res = sqlite3_prepare(g_workspace, g_sql_buf[0], -1, &stmt, 0); 
-
 
464
        if (_sqlite_error(res)) goto vecmath_prepare_error;
-
 
465
        res = sqlite3_bind_double(stmt, 1, base);
-
 
466
    } else {
457
    sprintf(g_sql_buf[0], "insert into [%s].sdf_data([row name], V1) "
467
        sprintf(g_sql_buf[0], "insert into [%s].sdf_data([row name], V1) "
458
            "select [row name], %s([%s]) from [%s].sdf_data", iname, funcname,
468
                "select [row name], %s([%s]) from [%s].sdf_data", iname, funcname,
459
            varname_src, iname_src);
469
                varname_src, iname_src);
460
 
-
 
461
    res = sqlite3_prepare(g_workspace, g_sql_buf[0], -1, &stmt, 0); 
470
        res = sqlite3_prepare(g_workspace, g_sql_buf[0], -1, &stmt, 0); 
-
 
471
    }
-
 
472
 
462
    if (_sqlite_error(res)) {
473
    if (_sqlite_error(res)) {
-
 
474
vecmath_prepare_error:
463
        sprintf(g_sql_buf[0], "detach %s", iname);
475
        sprintf(g_sql_buf[0], "detach %s", iname);
464
        _sqlite_exec(g_sql_buf[0]);
476
        _sqlite_exec(g_sql_buf[0]);
465
 
477
 
466
        /* we will return a string with the file name, and do file.remove
478
        /* we will return a string with the file name, and do file.remove
467
         * at R */
479
         * at R */
Line 478... Line 490...
478
    UNUSE_SDF2(iname_src);
490
    UNUSE_SDF2(iname_src);
479
 
491
 
480
    return _create_svector_sexp(iname, "V1", "numeric");
492
    return _create_svector_sexp(iname, "V1", "numeric");
481
}
493
}
482
 
494
 
483
SEXP sdf_do_variable_op(SEXP func, SEXP vector, SEXP op2) {
495
SEXP sdf_do_variable_op(SEXP func, SEXP vector, SEXP op2, SEXP arg_reversed) {
484
    char *iname = NULL, *iname_src, *varname_src, *funcname;
496
    char *iname = NULL, *iname_src, *varname_src, *funcname;
485
    int res, functype = -1, op2_len, svec_len, i;
497
    int res, functype = -1, op2_len, svec_len, i, reversed;
486
    sqlite3_stmt *stmt, *stmt2;
498
    sqlite3_stmt *stmt, *stmt2;
487
 
499
 
488
    /* get data from arguments (function name and sqlite.vector stuffs) */
500
    /* get data from arguments (function name and sqlite.vector stuffs) */
489
    funcname = CHAR_ELT(func, 0);
501
    funcname = CHAR_ELT(func, 0);
490
    iname_src = SDF_INAME(vector);
502
    iname_src = SDF_INAME(vector);
491
    varname_src = SVEC_VARNAME(vector);
503
    varname_src = SVEC_VARNAME(vector);
-
 
504
    reversed = LOGICAL(arg_reversed)[0];
492
 
505
 
493
    if (!USE_SDF1(iname_src, TRUE, TRUE)) return R_NilValue;
506
    if (!USE_SDF1(iname_src, TRUE, TRUE)) return R_NilValue;
494
    switch(funcname[0]) {
507
    switch(funcname[0]) {
495
        case '+' :
508
        case '+' :
496
        case '-' :
509
        case '-' :
Line 511... Line 524...
511
 
524
 
512
    svec_len = _get_row_count2(iname_src, 1);
525
    svec_len = _get_row_count2(iname_src, 1);
513
    if (functype == 0 || functype == 2 || (functype == 1 && funcname[0] != '!')) {
526
    if (functype == 0 || functype == 2 || (functype == 1 && funcname[0] != '!')) {
514
        char *insert_fmt_string1c, *insert_fmt_string1s;
527
        char *insert_fmt_string1c, *insert_fmt_string1s;
515
        char *insert_fmt_string2c, *insert_fmt_string2s;
528
        char *insert_fmt_string2c, *insert_fmt_string2s;
-
 
529
        int vec_idx, sdf_idx;
-
 
530
 
516
        iname = _create_svector1(R_NilValue, (functype == 0) ? "double" : "bit", NULL, TRUE);
531
        iname = _create_svector1(R_NilValue, (functype == 0) ? "double" : "bit", NULL, TRUE);
517
 
532
 
-
 
533
        /* insert_fmt_string prefixes:
-
 
534
         * 1 - op2 is an ordinary vector, op2_len = 1, straightforward insert-select
-
 
535
         * 2 - op2 is an ordinary vector, op2_len > 1, may need recycling, loop both sides
-
 
536
         * s - operator will be printed as string
-
 
537
         * c - operator is either INTDIV or RMOD (int division, R modulo). initially, I
-
 
538
         *     thought I could cast both op to int then use / and % of sqlite, which is just
-
 
539
         *     the 2nd character of the funcname. however, R's INTDIV and casts to int 
-
 
540
         *     after division (e.g. 3.5 %/% 1.5 == 2). RMOD operates on doubles too,
-
 
541
         *     which is the remainder of the largest int multiple of "divisor"
-
 
542
         *     (e.g. 3.5 %% 1.5 = 0.5)
-
 
543
         */ 
518
        if (functype == 1) { /* boolean binary operators */
544
        if (functype == 1) { /* boolean binary operators */
-
 
545
            if (!reversed) {
519
            insert_fmt_string1s = "insert into [%s].sdf_data "
546
                insert_fmt_string1s = "insert into [%s].sdf_data "
520
                        "select [row name], ([%s] != 0) %s (? != 0) from [%s].sdf_data";
547
                            "select [row name], ([%s] != 0) %s (? != 0) from [%s].sdf_data";
-
 
548
            } else {
-
 
549
                insert_fmt_string1s = "insert into [%s].sdf_data "
-
 
550
                            "select [row name], (? != 0) %s ([%s] != 0) from [%s].sdf_data";
-
 
551
            }
521
            insert_fmt_string2s = "insert into [%s].sdf_data values(?, (? != 0) %s (? != 0))";
552
            insert_fmt_string2s = "insert into [%s].sdf_data values(?, (? != 0) %s (? != 0))";
522
            /* no need for char version of fmt_string2, since %% only occurs for functype==0 */
553
            /* no need for char version of fmt_string2, since %% only occurs for functype==0 */
523
            insert_fmt_string1c = insert_fmt_string1s;
554
            insert_fmt_string1c = insert_fmt_string1s;
524
            insert_fmt_string2c = insert_fmt_string2s;
555
            insert_fmt_string2c = insert_fmt_string2s;
525
        } else {
556
        } else {
-
 
557
            if (!reversed) {
526
            insert_fmt_string1s = "insert into [%s].sdf_data "
558
                insert_fmt_string1s = "insert into [%s].sdf_data "
527
                        "select [row name], [%s] %s ? from [%s].sdf_data";
559
                            "select [row name], [%s] %s ? from [%s].sdf_data";
528
            insert_fmt_string1c = "insert into [%s].sdf_data "
560
                insert_fmt_string1c = "insert into [%s].sdf_data "
529
                        "select [row name], [%s] %c ? from [%s].sdf_data";
561
                            "select [row name], %s([%s],?) from [%s].sdf_data";
-
 
562
            } else {
-
 
563
                insert_fmt_string1s = "insert into [%s].sdf_data "
-
 
564
                            "select [row name], ? %s [%s] from [%s].sdf_data";
-
 
565
                insert_fmt_string1c = "insert into [%s].sdf_data "
-
 
566
                            "select [row name], %s(?,[%s]) from [%s].sdf_data";
-
 
567
            }
530
            /* fmt_string2c format operator from a char, used for %% and %/% */
568
            /* fmt_string2c format operator from a char, used for %% and %/% */
531
            /* BUG: i'm casting to int before applying / & %, w/c is different
-
 
532
             * from R. added trunc to pass package test */
-
 
533
            insert_fmt_string2c = "insert into [%s].sdf_data values(?, trunc(? %c ?))";
569
            insert_fmt_string2c = "insert into [%s].sdf_data values(?, %s(?,?))";
534
            insert_fmt_string2s = "insert into [%s].sdf_data values(?, ? %s ?)";
570
            insert_fmt_string2s = "insert into [%s].sdf_data values(?, ? %s ?)";
535
        }
571
        }
536
 
572
 
-
 
573
        /* for 2* insert statements, the values below specifies the index of bind().
-
 
574
         * if !reversed, then e1 is svec, e2 is anything. otherwise, e2 is the svec */
-
 
575
        if (reversed) { sdf_idx = 3; vec_idx = 2; }
-
 
576
        else { sdf_idx = 2; vec_idx = 3; }
537
 
577
 
538
        if (IS_NUMERIC(op2)) {
578
        if (IS_NUMERIC(op2)) {
539
            op2_len = LENGTH(op2);
579
            op2_len = LENGTH(op2);
540
 
580
 
541
            if (op2_len == 1) {
581
            if (op2_len == 1) {
542
                if (funcname[0] == '%') {
582
                if (funcname[0] == '%') {
543
                    sprintf(g_sql_buf[2], insert_fmt_string1c, iname, 
583
                    sprintf(g_sql_buf[2], insert_fmt_string1c, iname, 
544
                            varname_src, funcname[1], iname_src);
584
                            (funcname[1] == '%') ? "r_mod" : "r_intdiv", varname_src, iname_src);
545
                } else {
585
                } else {
546
                    sprintf(g_sql_buf[2], insert_fmt_string1s, iname,
586
                    sprintf(g_sql_buf[2], insert_fmt_string1s, iname,
547
                            varname_src, funcname, iname_src);
587
                            varname_src, funcname, iname_src);
548
                }
588
                }
549
                res = sqlite3_prepare(g_workspace, g_sql_buf[2], -1, &stmt, 0);
589
                res = sqlite3_prepare(g_workspace, g_sql_buf[2], -1, &stmt, 0);
Line 556... Line 596...
556
                        varname_src, iname_src);
596
                        varname_src, iname_src);
557
                res = sqlite3_prepare(g_workspace, g_sql_buf[2], -1, &stmt2, 0);
597
                res = sqlite3_prepare(g_workspace, g_sql_buf[2], -1, &stmt2, 0);
558
                _sqlite_error(res);
598
                _sqlite_error(res);
559
 
599
 
560
                if (funcname[0] == '%') {
600
                if (funcname[0] == '%') {
561
                    /* sqlite does int div with "/" if both args are int. mod is % also.
601
                    sprintf(g_sql_buf[2], insert_fmt_string2c, iname, 
562
                     * fortunately, in both cases the sqlite op is 2nd char of funcname */
-
 
563
                    sprintf(g_sql_buf[2], insert_fmt_string2c, iname, funcname[1]);  
602
                            (funcname[1] == '%') ? "r_mod" : "r_intdiv");  
564
                    _sqlite_begin;
603
                    _sqlite_begin;
565
                    res = sqlite3_prepare(g_workspace, g_sql_buf[2], -1, &stmt, 0);
604
                    res = sqlite3_prepare(g_workspace, g_sql_buf[2], -1, &stmt, 0);
566
                    _sqlite_error(res);
605
                    _sqlite_error(res);
567
 
606
 
568
                    for (i = 0; i < svec_len; i++) {
607
                    for (i = 0; i < svec_len; i++) {
569
                        sqlite3_step(stmt2);
608
                        sqlite3_step(stmt2);
570
 
609
 
571
                        sqlite3_reset(stmt);
610
                        sqlite3_reset(stmt);
572
                        sqlite3_bind_text(stmt, 1, (char *)sqlite3_column_text(stmt2, 0), -1, SQLITE_STATIC);
611
                        sqlite3_bind_text(stmt, 1, (char *)sqlite3_column_text(stmt2, 0), -1, SQLITE_STATIC);
573
                        sqlite3_bind_int(stmt, 2, (int)sqlite3_column_double(stmt2, 1));
612
                        sqlite3_bind_int(stmt, sdf_idx, (int)sqlite3_column_double(stmt2, 1));
574
                        sqlite3_bind_int(stmt, 3, (int)REAL(op2)[i % op2_len]);
613
                        sqlite3_bind_int(stmt, vec_idx, (int)REAL(op2)[i % op2_len]);
575
                        sqlite3_step(stmt);
614
                        sqlite3_step(stmt);
576
                    }
615
                    }
577
                    sqlite3_finalize(stmt);
616
                    sqlite3_finalize(stmt);
578
                    sqlite3_finalize(stmt2);
617
                    sqlite3_finalize(stmt2);
579
                    _sqlite_commit;
618
                    _sqlite_commit;
Line 586... Line 625...
586
                    for (i = 0; i < svec_len; i++) {
625
                    for (i = 0; i < svec_len; i++) {
587
                        sqlite3_step(stmt2);
626
                        sqlite3_step(stmt2);
588
 
627
 
589
                        sqlite3_reset(stmt);
628
                        sqlite3_reset(stmt);
590
                        sqlite3_bind_text(stmt, 1, (char *)sqlite3_column_text(stmt2, 0), -1, SQLITE_STATIC);
629
                        sqlite3_bind_text(stmt, 1, (char *)sqlite3_column_text(stmt2, 0), -1, SQLITE_STATIC);
591
                        sqlite3_bind_double(stmt, 2, sqlite3_column_double(stmt2, 1));
630
                        sqlite3_bind_double(stmt, sdf_idx, sqlite3_column_double(stmt2, 1));
592
                        sqlite3_bind_double(stmt, 3, REAL(op2)[i % op2_len]);
631
                        sqlite3_bind_double(stmt, vec_idx, REAL(op2)[i % op2_len]);
593
                        sqlite3_step(stmt);
632
                        sqlite3_step(stmt);
594
                    }
633
                    }
595
                    sqlite3_finalize(stmt);
634
                    sqlite3_finalize(stmt);
596
                    sqlite3_finalize(stmt2);
635
                    sqlite3_finalize(stmt2);
597
                    _sqlite_commit;
636
                    _sqlite_commit;
Line 599... Line 638...
599
            } else { /* op2_len > svec_len, recycle svec */
638
            } else { /* op2_len > svec_len, recycle svec */
600
                sprintf(g_sql_buf[1], "select [%s] from [%s].sdf_data",
639
                sprintf(g_sql_buf[1], "select [%s] from [%s].sdf_data",
601
                        varname_src, iname_src);
640
                        varname_src, iname_src);
602
 
641
 
603
                if (funcname[0] == '%') {
642
                if (funcname[0] == '%') {
604
                    sprintf(g_sql_buf[2], insert_fmt_string2c, iname, funcname[1]);  
643
                    sprintf(g_sql_buf[2], insert_fmt_string2c, iname, 
-
 
644
                            (funcname[1] == '%') ? "r_mod" : "r_intdiv");
605
                    res = sqlite3_prepare(g_workspace, g_sql_buf[2], -1, &stmt, 0);
645
                    res = sqlite3_prepare(g_workspace, g_sql_buf[2], -1, &stmt, 0);
606
                    _sqlite_error(res);
646
                    _sqlite_error(res);
607
                } else {
647
                } else {
608
                    sprintf(g_sql_buf[2], insert_fmt_string2s, iname, funcname);
648
                    sprintf(g_sql_buf[2], insert_fmt_string2s, iname, funcname);
609
                    res = sqlite3_prepare(g_workspace, g_sql_buf[2], -1, &stmt, 0);
649
                    res = sqlite3_prepare(g_workspace, g_sql_buf[2], -1, &stmt, 0);
Line 621... Line 661...
621
 
661
 
622
                            sqlite3_reset(stmt);
662
                            sqlite3_reset(stmt);
623
                            /* simplify my life, just use ints for row names so that we
663
                            /* simplify my life, just use ints for row names so that we
624
                             * don't have to worry about duplicates */
664
                             * don't have to worry about duplicates */
625
                            sqlite3_bind_int(stmt, 1, i); 
665
                            sqlite3_bind_int(stmt, 1, i); 
626
                            sqlite3_bind_int(stmt, 2, sqlite3_column_int(stmt2, 1));
666
                            sqlite3_bind_int(stmt, sdf_idx, sqlite3_column_int(stmt2, 1));
627
                            sqlite3_bind_int(stmt, 3, (int)REAL(op2)[i % op2_len]);
667
                            sqlite3_bind_int(stmt, vec_idx, (int)REAL(op2)[i % op2_len]);
628
                            sqlite3_step(stmt);
668
                            sqlite3_step(stmt);
629
                        }
669
                        }
630
                    } else {
670
                    } else {
631
                        for ( ; i < op2_len && sqlite3_step(stmt) == SQLITE_ROW ; i++) {
671
                        for ( ; i < op2_len && sqlite3_step(stmt) == SQLITE_ROW ; i++) {
632
                            sqlite3_step(stmt2);
672
                            sqlite3_step(stmt2);
633
 
673
 
634
                            sqlite3_reset(stmt);
674
                            sqlite3_reset(stmt);
635
                            sqlite3_bind_int(stmt, 1, i);
675
                            sqlite3_bind_int(stmt, 1, i);
636
                            sqlite3_bind_double(stmt, 2, sqlite3_column_double(stmt2, 1));
676
                            sqlite3_bind_double(stmt, sdf_idx, sqlite3_column_double(stmt2, 1));
637
                            sqlite3_bind_double(stmt, 3, REAL(op2)[i % op2_len]);
677
                            sqlite3_bind_double(stmt, vec_idx, REAL(op2)[i % op2_len]);
638
                            sqlite3_step(stmt);
678
                            sqlite3_step(stmt);
639
                        }
679
                        }
640
                    }
680
                    }
641
 
681
 
642
                    /* recycle on svec if we loop again */
682
                    /* recycle on svec if we loop again */
Line 653... Line 693...
653
            op2_len = LENGTH(op2);
693
            op2_len = LENGTH(op2);
654
 
694
 
655
            if (op2_len == 1) {
695
            if (op2_len == 1) {
656
                if (funcname[0] == '%') {
696
                if (funcname[0] == '%') {
657
                    sprintf(g_sql_buf[2], insert_fmt_string1c, iname, 
697
                    sprintf(g_sql_buf[2], insert_fmt_string1c, iname, 
658
                            varname_src, funcname[1], iname_src);
698
                            varname_src, (funcname[1] == '%') ? "r_mod" : "r_intdiv", iname_src);
659
                } else {
699
                } else {
660
                    sprintf(g_sql_buf[2], insert_fmt_string1s, iname,
700
                    sprintf(g_sql_buf[2], insert_fmt_string1s, iname,
661
                            varname_src, funcname, iname_src);
701
                            varname_src, funcname, iname_src);
662
                }
702
                }
663
                res = sqlite3_prepare(g_workspace, g_sql_buf[2], -1, &stmt, 0);
703
                res = sqlite3_prepare(g_workspace, g_sql_buf[2], -1, &stmt, 0);
Line 671... Line 711...
671
                _sqlite_error(res);
711
                _sqlite_error(res);
672
 
712
 
673
                if (funcname[0] == '%') {
713
                if (funcname[0] == '%') {
674
                    /* sqlite does int div with "/" if both args are int. mod is % also.
714
                    /* sqlite does int div with "/" if both args are int. mod is % also.
675
                     * fortunately, in both cases the sqlite op is 2nd char of funcname */
715
                     * fortunately, in both cases the sqlite op is 2nd char of funcname */
676
                    sprintf(g_sql_buf[2], insert_fmt_string2c, iname, funcname[1]);  
716
                    sprintf(g_sql_buf[2], insert_fmt_string2c, iname, 
-
 
717
                            (funcname[1] == '%') ? "r_mod" : "r_intdiv");
677
                    _sqlite_begin;
718
                    _sqlite_begin;
678
                    res = sqlite3_prepare(g_workspace, g_sql_buf[2], -1, &stmt, 0);
719
                    res = sqlite3_prepare(g_workspace, g_sql_buf[2], -1, &stmt, 0);
679
                    _sqlite_error(res);
720
                    _sqlite_error(res);
680
 
721
 
681
                    for (i = 0; i < svec_len; i++) {
722
                    for (i = 0; i < svec_len; i++) {
682
                        sqlite3_step(stmt2);
723
                        sqlite3_step(stmt2);
683
 
724
 
684
                        sqlite3_reset(stmt);
725
                        sqlite3_reset(stmt);
685
                        sqlite3_bind_text(stmt, 1, (char *)sqlite3_column_text(stmt2, 0), -1, SQLITE_STATIC);
726
                        sqlite3_bind_text(stmt, 1, (char *)sqlite3_column_text(stmt2, 0), -1, SQLITE_STATIC);
686
                        sqlite3_bind_int(stmt, 2, sqlite3_column_int(stmt2, 1));
727
                        sqlite3_bind_int(stmt, sdf_idx, sqlite3_column_int(stmt2, 1));
687
                        sqlite3_bind_int(stmt, 3, INTEGER(op2)[i % op2_len]);
728
                        sqlite3_bind_int(stmt, vec_idx, INTEGER(op2)[i % op2_len]);
688
                        sqlite3_step(stmt);
729
                        sqlite3_step(stmt);
689
                    }
730
                    }
690
                    _sqlite_commit;
731
                    _sqlite_commit;
691
                } else {
732
                } else {
692
                    sprintf(g_sql_buf[2], insert_fmt_string2s, iname, funcname);
733
                    sprintf(g_sql_buf[2], insert_fmt_string2s, iname, funcname);
Line 697... Line 738...
697
                    for (i = 0; i < svec_len; i++) {
738
                    for (i = 0; i < svec_len; i++) {
698
                        sqlite3_step(stmt2);
739
                        sqlite3_step(stmt2);
699
 
740
 
700
                        sqlite3_reset(stmt);
741
                        sqlite3_reset(stmt);
701
                        sqlite3_bind_text(stmt, 1, (char *)sqlite3_column_text(stmt2, 0), -1, SQLITE_STATIC);
742
                        sqlite3_bind_text(stmt, 1, (char *)sqlite3_column_text(stmt2, 0), -1, SQLITE_STATIC);
702
                        sqlite3_bind_double(stmt, 2, sqlite3_column_double(stmt2, 1));
743
                        sqlite3_bind_double(stmt, sdf_idx, sqlite3_column_double(stmt2, 1));
703
                        sqlite3_bind_double(stmt, 3, (double)INTEGER(op2)[i % op2_len]);
744
                        sqlite3_bind_double(stmt, vec_idx, (double)INTEGER(op2)[i % op2_len]);
704
                        sqlite3_step(stmt);
745
                        sqlite3_step(stmt);
705
                    }
746
                    }
706
                    _sqlite_commit;
747
                    _sqlite_commit;
707
                }
748
                }
708
                sqlite3_finalize(stmt2);
749
                sqlite3_finalize(stmt2);
709
            } else {
750
            } else {
710
                sprintf(g_sql_buf[1], "select [%s] from [%s].sdf_data",
751
                sprintf(g_sql_buf[1], "select [%s] from [%s].sdf_data",
711
                        varname_src, iname_src);
752
                        varname_src, iname_src);
712
 
753
 
713
                if (funcname[0] == '%') {
754
                if (funcname[0] == '%') {
714
                    sprintf(g_sql_buf[2], insert_fmt_string2c, iname, funcname[1]);  
755
                    sprintf(g_sql_buf[2], insert_fmt_string2c, iname,
-
 
756
                            (funcname[1] == '%') ? "r_mod" : "r_intdiv");
715
                    res = sqlite3_prepare(g_workspace, g_sql_buf[2], -1, &stmt, 0);
757
                    res = sqlite3_prepare(g_workspace, g_sql_buf[2], -1, &stmt, 0);
716
                    _sqlite_error(res);
758
                    _sqlite_error(res);
717
                } else {
759
                } else {
718
                    sprintf(g_sql_buf[2], insert_fmt_string2s, iname, funcname);
760
                    sprintf(g_sql_buf[2], insert_fmt_string2s, iname, funcname);
719
                    res = sqlite3_prepare(g_workspace, g_sql_buf[2], -1, &stmt, 0);
761
                    res = sqlite3_prepare(g_workspace, g_sql_buf[2], -1, &stmt, 0);
Line 731... Line 773...
731
 
773
 
732
                            sqlite3_reset(stmt);
774
                            sqlite3_reset(stmt);
733
                            /* simplify my life, just use ints for row names so that we
775
                            /* simplify my life, just use ints for row names so that we
734
                             * don't have to worry about duplicates */
776
                             * don't have to worry about duplicates */
735
                            sqlite3_bind_int(stmt, 1, i); 
777
                            sqlite3_bind_int(stmt, 1, i); 
736
                            sqlite3_bind_int(stmt, 2, sqlite3_column_int(stmt2, 1));
778
                            sqlite3_bind_int(stmt, sdf_idx, sqlite3_column_int(stmt2, 1));
737
                            sqlite3_bind_int(stmt, 3, INTEGER(op2)[i % op2_len]);
779
                            sqlite3_bind_int(stmt, vec_idx, INTEGER(op2)[i % op2_len]);
738
                            sqlite3_step(stmt);
780
                            sqlite3_step(stmt);
739
                        }
781
                        }
740
                    } else {
782
                    } else {
741
                        for ( ; i < op2_len && sqlite3_step(stmt) == SQLITE_ROW ; i++) {
783
                        for ( ; i < op2_len && sqlite3_step(stmt) == SQLITE_ROW ; i++) {
742
                            sqlite3_step(stmt2);
784
                            sqlite3_step(stmt2);
743
 
785
 
744
                            sqlite3_reset(stmt);
786
                            sqlite3_reset(stmt);
745
                            sqlite3_bind_int(stmt, 1, i);
787
                            sqlite3_bind_int(stmt, 1, i);
746
                            sqlite3_bind_double(stmt, 2, sqlite3_column_double(stmt2, 1));
788
                            sqlite3_bind_double(stmt, sdf_idx, sqlite3_column_double(stmt2, 1));
747
                            sqlite3_bind_double(stmt, 3, (double)INTEGER(op2)[i % op2_len]);
789
                            sqlite3_bind_double(stmt, vec_idx, (double)INTEGER(op2)[i % op2_len]);
748
                            sqlite3_step(stmt);
790
                            sqlite3_step(stmt);
749
                        }
791
                        }
750
                    }
792
                    }
751
 
793
 
752
                    /* recycle on svec if we loop again */
794
                    /* recycle on svec if we loop again */
Line 756... Line 798...
756
            }
798
            }
757
 
799
 
758
            sqlite3_finalize(stmt);
800
            sqlite3_finalize(stmt);
759
        } else if (inherits(op2, "sqlite.vector")) { 
801
        } else if (inherits(op2, "sqlite.vector")) { 
760
            /* op2 is surely not a factor, as handled by the R wrapper */
802
            /* op2 is surely not a factor, as handled by the R wrapper */
-
 
803
            /* even though it is impossible for reversed to be FALSE, still use
-
 
804
             * sdf_idx and vec_idx so that code would be less confusing */
761
            char *iname_op2, *varname_op2;
805
            char *iname_op2, *varname_op2;
762
            sqlite3_stmt *stmt3;
806
            sqlite3_stmt *stmt3;
763
            iname_op2 = SDF_INAME(op2);
807
            iname_op2 = SDF_INAME(op2);
764
            varname_op2 = SVEC_VARNAME(op2);
808
            varname_op2 = SVEC_VARNAME(op2);
765
 
809
 
Line 780... Line 824...
780
            sprintf(g_sql_buf[2], "select [%s] from [%s].sdf_data", varname_op2, iname_op2);
824
            sprintf(g_sql_buf[2], "select [%s] from [%s].sdf_data", varname_op2, iname_op2);
781
            res = sqlite3_prepare(g_workspace, g_sql_buf[2], -1, &stmt3, 0);
825
            res = sqlite3_prepare(g_workspace, g_sql_buf[2], -1, &stmt3, 0);
782
            _sqlite_error(res);
826
            _sqlite_error(res);
783
 
827
 
784
            if (funcname[0] == '%') {
828
            if (funcname[0] == '%') {
785
                sprintf(g_sql_buf[2], insert_fmt_string2c, iname, funcname[1]);
829
                sprintf(g_sql_buf[2], insert_fmt_string2c, iname,
-
 
830
                            (funcname[1] == '%') ? "r_mod" : "r_intdiv");
786
                res = sqlite3_prepare(g_workspace, g_sql_buf[2], -1, &stmt, 0);
831
                res = sqlite3_prepare(g_workspace, g_sql_buf[2], -1, &stmt, 0);
787
                _sqlite_error(res);
832
                _sqlite_error(res);
788
 
833
 
789
                if (svec_len == op2_len) {
834
                if (svec_len == op2_len) {
790
                    for (i = 0; i < svec_len; i++) {
835
                    for (i = 0; i < svec_len; i++) {
791
                        sqlite3_step(stmt2); sqlite3_step(stmt3);
836
                        sqlite3_step(stmt2); sqlite3_step(stmt3);
792
 
837
 
793
                        sqlite3_reset(stmt);
838
                        sqlite3_reset(stmt);
794
                        sqlite3_bind_int(stmt, 1, i);
839
                        sqlite3_bind_int(stmt, 1, i);
795
                        sqlite3_bind_int(stmt, 2, sqlite3_column_int(stmt2, 0));
840
                        sqlite3_bind_int(stmt, sdf_idx, sqlite3_column_int(stmt2, 0));
796
                        sqlite3_bind_int(stmt, 3, sqlite3_column_int(stmt3, 0));
841
                        sqlite3_bind_int(stmt, vec_idx, sqlite3_column_int(stmt3, 0));
797
                        sqlite3_step(stmt);
842
                        sqlite3_step(stmt);
798
                    }
843
                    }
799
                } else if (svec_len < op2_len) {
844
                } else if (svec_len < op2_len) {
800
                    i = 0;
845
                    i = 0;
801
                    while (i < op2_len) {
846
                    while (i < op2_len) {
802
                        for ( ; sqlite3_step(stmt2) == SQLITE_ROW && i < op2_len; i++) {
847
                        for ( ; sqlite3_step(stmt2) == SQLITE_ROW && i < op2_len; i++) {
803
                            sqlite3_step(stmt3);
848
                            sqlite3_step(stmt3);
804
 
849
 
805
                            sqlite3_reset(stmt);
850
                            sqlite3_reset(stmt);
806
                            sqlite3_bind_int(stmt, 1, i);
851
                            sqlite3_bind_int(stmt, 1, i);
807
                            sqlite3_bind_int(stmt, 2, sqlite3_column_int(stmt2, 0));
852
                            sqlite3_bind_int(stmt, sdf_idx, sqlite3_column_int(stmt2, 0));
808
                            sqlite3_bind_int(stmt, 3, sqlite3_column_int(stmt3, 0));
853
                            sqlite3_bind_int(stmt, vec_idx, sqlite3_column_int(stmt3, 0));
809
                            sqlite3_step(stmt);
854
                            sqlite3_step(stmt);
810
                        }
855
                        }
811
                        sqlite3_reset(stmt2);
856
                        sqlite3_reset(stmt2);
812
                    }
857
                    }
813
                } else {
858
                } else {
Line 816... Line 861...
816
                        for ( ; sqlite3_step(stmt3) == SQLITE_ROW && i < svec_len; i++) {
861
                        for ( ; sqlite3_step(stmt3) == SQLITE_ROW && i < svec_len; i++) {
817
                            sqlite3_step(stmt2);
862
                            sqlite3_step(stmt2);
818
 
863
 
819
                            sqlite3_reset(stmt);
864
                            sqlite3_reset(stmt);
820
                            sqlite3_bind_int(stmt, 1, i);
865
                            sqlite3_bind_int(stmt, 1, i);
821
                            sqlite3_bind_int(stmt, 2, sqlite3_column_int(stmt2, 0));
866
                            sqlite3_bind_int(stmt, sdf_idx, sqlite3_column_int(stmt2, 0));
822
                            sqlite3_bind_int(stmt, 3, sqlite3_column_int(stmt3, 0));
867
                            sqlite3_bind_int(stmt, vec_idx, sqlite3_column_int(stmt3, 0));
823
                            sqlite3_step(stmt);
868
                            sqlite3_step(stmt);
824
                        }
869
                        }
825
                        sqlite3_reset(stmt3);
870
                        sqlite3_reset(stmt3);
826
                    }
871
                    }
827
                }
872
                }
Line 835... Line 880...
835
                    for (i = 0; i < svec_len; i++) {
880
                    for (i = 0; i < svec_len; i++) {
836
                        sqlite3_step(stmt2); sqlite3_step(stmt3);
881
                        sqlite3_step(stmt2); sqlite3_step(stmt3);
837
 
882
 
838
                        sqlite3_reset(stmt);
883
                        sqlite3_reset(stmt);
839
                        sqlite3_bind_int(stmt, 1, i);
884
                        sqlite3_bind_int(stmt, 1, i);
840
                        sqlite3_bind_double(stmt, 2, sqlite3_column_double(stmt2, 0));
885
                        sqlite3_bind_double(stmt, sdf_idx, sqlite3_column_double(stmt2, 0));
841
                        sqlite3_bind_double(stmt, 3, sqlite3_column_double(stmt3, 0));
886
                        sqlite3_bind_double(stmt, vec_idx, sqlite3_column_double(stmt3, 0));
842
                        sqlite3_step(stmt);
887
                        sqlite3_step(stmt);
843
                    }
888
                    }
844
                } else if (svec_len < op2_len) { /* recycle svec */
889
                } else if (svec_len < op2_len) { /* recycle svec */
845
                    i = 0;
890
                    i = 0;
846
                    while (i < op2_len) {
891
                    while (i < op2_len) {
847
                        for ( ; sqlite3_step(stmt2) == SQLITE_ROW && i < op2_len; i++) {
892
                        for ( ; sqlite3_step(stmt2) == SQLITE_ROW && i < op2_len; i++) {
848
                            sqlite3_step(stmt3);
893
                            sqlite3_step(stmt3);
849
 
894
 
850
                            sqlite3_reset(stmt);
895
                            sqlite3_reset(stmt);
851
                            sqlite3_bind_int(stmt, 1, i);
896
                            sqlite3_bind_int(stmt, 1, i);
852
                            sqlite3_bind_double(stmt, 2, sqlite3_column_double(stmt2, 0));
897
                            sqlite3_bind_double(stmt, sdf_idx, sqlite3_column_double(stmt2, 0));
853
                            sqlite3_bind_double(stmt, 3, sqlite3_column_double(stmt3, 0));
898
                            sqlite3_bind_double(stmt, vec_idx, sqlite3_column_double(stmt3, 0));
854
                            sqlite3_step(stmt);
899
                            sqlite3_step(stmt);
855
                        }
900
                        }
856
                        sqlite3_reset(stmt2);
901
                        sqlite3_reset(stmt2);
857
                    }
902
                    }
858
                } else { /* svec_len > op2_len, recycle op2 */
903
                } else { /* svec_len > op2_len, recycle op2 */
Line 861... Line 906...
861
                        for ( ; sqlite3_step(stmt3) == SQLITE_ROW && i < svec_len; i++) {
906
                        for ( ; sqlite3_step(stmt3) == SQLITE_ROW && i < svec_len; i++) {
862
                            sqlite3_step(stmt2);
907
                            sqlite3_step(stmt2);
863
 
908
 
864
                            sqlite3_reset(stmt);
909
                            sqlite3_reset(stmt);
865
                            sqlite3_bind_int(stmt, 1, i);
910
                            sqlite3_bind_int(stmt, 1, i);
866
                            sqlite3_bind_double(stmt, 2, sqlite3_column_double(stmt2, 0));
911
                            sqlite3_bind_double(stmt, sdf_idx, sqlite3_column_double(stmt2, 0));
867
                            sqlite3_bind_double(stmt, 3, sqlite3_column_double(stmt3, 0));
912
                            sqlite3_bind_double(stmt, vec_idx, sqlite3_column_double(stmt3, 0));
868
                            sqlite3_step(stmt);
913
                            sqlite3_step(stmt);
869
                        }
914
                        }
870
                        sqlite3_reset(stmt3);
915
                        sqlite3_reset(stmt3);
871
                    }
916
                    }
872
                }
917
                }
Line 1010... Line 1055...
1010
 
1055
 
1011
/****************************************************************************
1056
/****************************************************************************
1012
 * VECTOR MATH/OPS/GROUP OPERATIONS
1057
 * VECTOR MATH/OPS/GROUP OPERATIONS
1013
 ****************************************************************************/
1058
 ****************************************************************************/
1014
 
1059
 
1015
int __vecmath_checkarg(sqlite3_context *ctx, sqlite3_value *arg, double *value) {
1060
R_INLINE int __vecmath_checkarg(sqlite3_context *ctx, sqlite3_value *arg, double *value) {
1016
    int ret = 1;
1061
    int ret = 1;
1017
    if (sqlite3_value_type(arg) == SQLITE_NULL) { 
1062
    if (sqlite3_value_type(arg) == SQLITE_NULL) { 
1018
        sqlite3_result_null(ctx); 
1063
        sqlite3_result_null(ctx); 
1019
        ret = 0;
1064
        ret = 0;
1020
    } else {
1065
    } else {
Line 1031... Line 1076...
1031
    if (__vecmath_checkarg(ctx, argv[0], &value)) { \
1076
    if (__vecmath_checkarg(ctx, argv[0], &value)) { \
1032
        sqlite3_result_double(ctx, func(value)); \
1077
        sqlite3_result_double(ctx, func(value)); \
1033
    }  \
1078
    }  \
1034
}
1079
}
1035
 
1080
 
-
 
1081
#define SQLITE_MATH_FUNC2(name, func) static void __vecmath_ ## name(\
-
 
1082
        sqlite3_context *ctx, int argc, sqlite3_value **argv) { \
-
 
1083
    double value1, value2; \
-
 
1084
    if (__vecmath_checkarg(ctx, argv[0], &value1) && \
-
 
1085
        __vecmath_checkarg(ctx, argv[1], &value2)) { \
-
 
1086
        sqlite3_result_double(ctx, func((long double)value1, (long double)value2)); \
-
 
1087
    }  \
-
 
1088
}
-
 
1089
 
1036
#define SQLITE_MATH_FUNC_CUM(name, func) static void __vecmath_ ## name(\
1090
#define SQLITE_MATH_FUNC_CUM(name, func) static void __vecmath_ ## name(\
1037
        sqlite3_context *ctx, int argc, sqlite3_value **argv) { \
1091
        sqlite3_context *ctx, int argc, sqlite3_value **argv) { \
1038
    double value; \
1092
    double value; \
1039
    if (__vecmath_checkarg(ctx, argv[0], &value)) { \
1093
    if (__vecmath_checkarg(ctx, argv[0], &value)) { \
1040
        if (g_start) { g_start = 0; g_accumulator = value; } \
1094
        if (g_start) { g_start = 0; g_accumulator = value; } \
1041
        else g_accumulator = func(g_accumulator, value); \
1095
        else g_accumulator = func(g_accumulator, value); \
1042
        sqlite3_result_double(ctx, g_accumulator); \
1096
        sqlite3_result_double(ctx, g_accumulator); \
1043
    }  \
1097
    }  \
1044
}
1098
}
1045
 
1099
 
-
 
1100
#define LOGBASE(a, b) log(a)/log(b)
-
 
1101
 
1046
/* SQLITE_MATH_FUNC1(abs, abs)   in SQLite */
1102
/* SQLITE_MATH_FUNC1(abs, abs)   in SQLite */
1047
SQLITE_MATH_FUNC1(sign, sign)   /* in R */
1103
SQLITE_MATH_FUNC1(sign, sign)   /* in R */
1048
SQLITE_MATH_FUNC1(sqrt, sqrt)
1104
SQLITE_MATH_FUNC1(sqrt, sqrt)
1049
SQLITE_MATH_FUNC1(floor, floor)
1105
SQLITE_MATH_FUNC1(floor, floor)
1050
SQLITE_MATH_FUNC1(ceiling, ceil)
1106
SQLITE_MATH_FUNC1(ceiling, ceil)
1051
SQLITE_MATH_FUNC1(trunc, ftrunc) /* in R */
1107
SQLITE_MATH_FUNC1(trunc, ftrunc) /* in R */
1052
/* SQLITE_MATH_FUNC1(round, )   in SQLite */
1108
/*SQLITE_MATH_FUNC2(round, fprec)  2 arg, in SQLite, but override with R's version */
1053
/* SQLITE_MATH_FUNC1(signif, ) 2 arg */
1109
SQLITE_MATH_FUNC2(signif, fround) /* 2 arg, in R */
1054
SQLITE_MATH_FUNC1(exp, exp)
1110
SQLITE_MATH_FUNC1(exp, exp)
1055
/* SQLITE_MATH_FUNC1(log, ) 2 arg */
1111
SQLITE_MATH_FUNC2(log, LOGBASE) /* 2 arg */
1056
SQLITE_MATH_FUNC1(cos, cos)
1112
SQLITE_MATH_FUNC1(cos, cos)
1057
SQLITE_MATH_FUNC1(sin, sin)
1113
SQLITE_MATH_FUNC1(sin, sin)
1058
SQLITE_MATH_FUNC1(tan, tan)
1114
SQLITE_MATH_FUNC1(tan, tan)
1059
SQLITE_MATH_FUNC1(acos, acos)
1115
SQLITE_MATH_FUNC1(acos, acos)
1060
SQLITE_MATH_FUNC1(asin, asin)
1116
SQLITE_MATH_FUNC1(asin, asin)
Line 1109... Line 1165...
1109
static void __vecsummary_finalize(sqlite3_context *ctx) {
1165
static void __vecsummary_finalize(sqlite3_context *ctx) {
1110
    /* g_accumulator already summarizes it. just return that */
1166
    /* g_accumulator already summarizes it. just return that */
1111
    sqlite3_result_double(ctx, g_accumulator);
1167
    sqlite3_result_double(ctx, g_accumulator);
1112
}
1168
}
1113
 
1169
 
-
 
1170
static void __r_modulo(sqlite3_context *ctx, int argc, sqlite3_value **argv) {
-
 
1171
    if (sqlite3_value_type(argv[0]) == SQLITE_NULL ||
-
 
1172
        sqlite3_value_type(argv[1]) == SQLITE_NULL) { 
-
 
1173
        sqlite3_result_null(ctx); 
-
 
1174
    } else {
-
 
1175
        double v1, v2, q, tmp;
-
 
1176
        if (sqlite3_value_type(argv[0]) == SQLITE_INTEGER && 
-
 
1177
            sqlite3_value_type(argv[1]) == SQLITE_INTEGER) {
-
 
1178
            int i1, i2;
-
 
1179
            i1 = sqlite3_value_int(argv[0]);
-
 
1180
            i2 = sqlite3_value_int(argv[1]);
-
 
1181
            if (i1 > 0 && i2 > 0) { 
-
 
1182
                sqlite3_result_int(ctx, i1 % i2); return;
-
 
1183
            }
-
 
1184
            v1 = i1; v2 = i2;
-
 
1185
        } else {
-
 
1186
            v1 = sqlite3_value_double(argv[0]);
-
 
1187
            v2 = sqlite3_value_double(argv[1]);
-
 
1188
        }
-
 
1189
        /* copied from myfmod() in src/main/arithmetic.c */
-
 
1190
        q = v1 / v2; 
-
 
1191
        if (v2 == 0) sqlite3_result_double(ctx, R_NaN);
-
 
1192
        tmp = v1 - floor(q) * v2;
-
 
1193
        /* checking omitted */
-
 
1194
        q = floor(tmp/v2);
-
 
1195
        sqlite3_result_double(ctx, tmp - q*v2);
-
 
1196
 
-
 
1197
    }
-
 
1198
}
-
 
1199
 
-
 
1200
static void __r_intdiv(sqlite3_context *ctx, int argc, sqlite3_value **argv) {
-
 
1201
    if (sqlite3_value_type(argv[0]) == SQLITE_NULL ||
-
 
1202
        sqlite3_value_type(argv[1]) == SQLITE_NULL) { 
-
 
1203
        sqlite3_result_null(ctx); 
-
 
1204
    } else {
-
 
1205
        double v1, v2;
-
 
1206
        if (sqlite3_value_type(argv[0]) == SQLITE_INTEGER && 
-
 
1207
            sqlite3_value_type(argv[1]) == SQLITE_INTEGER) {
-
 
1208
            int i1, i2;
-
 
1209
            i1 = sqlite3_value_int(argv[0]);
-
 
1210
            i2 = sqlite3_value_int(argv[1]);
-
 
1211
            if (i1 == NA_INTEGER || i2 == NA_INTEGER) {
-
 
1212
                sqlite3_result_int(ctx, NA_INTEGER); return;
-
 
1213
            } else if (i2 == 0) {
-
 
1214
                sqlite3_result_int(ctx, 0); return;
-
 
1215
            }
-
 
1216
            v1 = i1; v2 = i2;
-
 
1217
        } else {
-
 
1218
            v1 = sqlite3_value_double(argv[0]);
-
 
1219
            v2 = sqlite3_value_double(argv[1]);
-
 
1220
        }
-
 
1221
        /* copied from IDIVOP cases in src/main/arithmetic.c */
-
 
1222
        sqlite3_result_double(ctx, floor(v1/v2));
-
 
1223
    }
-
 
1224
}
1114
#define VMENTRY1(func)  {#func, __vecmath_ ## func}
1225
#define VMENTRY1(func)  {#func, __vecmath_ ## func}
1115
#define VSENTRY1(func)  {#func, __vecsummary_ ## func}
1226
#define VSENTRY1(func)  {#func, __vecsummary_ ## func}
1116
void __register_vector_math() {
1227
void __register_vector_math() {
1117
    int i, res;
1228
    int i, res;
1118
    static const struct {
1229
    static const struct {
Line 1143... Line 1254...
1143
        VMENTRY1(trigamma),
1254
        VMENTRY1(trigamma),
1144
        VMENTRY1(cumsum),
1255
        VMENTRY1(cumsum),
1145
        VMENTRY1(cumprod),
1256
        VMENTRY1(cumprod),
1146
        VMENTRY1(cummin),
1257
        VMENTRY1(cummin),
1147
        VMENTRY1(cummax)
1258
        VMENTRY1(cummax)
-
 
1259
    }, arr_func2[] =  {
-
 
1260
        {"r_mod", __r_modulo},
-
 
1261
        {"r_intdiv", __r_intdiv},
-
 
1262
        /*VMENTRY1(round),*/
-
 
1263
        VMENTRY1(signif),
-
 
1264
        VMENTRY1(log)
1148
    }, arr_sum1[] = {
1265
    }, arr_sum1[] = {
1149
        VSENTRY1(all_df),  /* can't override sum, min, max */
1266
        VSENTRY1(all_df),  /* can't override sum, min, max */
1150
        VSENTRY1(any_df),
1267
        VSENTRY1(any_df),
1151
        VSENTRY1(sum_df),
1268
        VSENTRY1(sum_df),
1152
        VSENTRY1(prod_df),
1269
        VSENTRY1(prod_df),
Line 1160... Line 1277...
1160
        res = sqlite3_create_function(g_workspace, arr_func1[i].name, 1, 
1277
        res = sqlite3_create_function(g_workspace, arr_func1[i].name, 1, 
1161
                SQLITE_ANY, NULL, arr_func1[i].func, NULL, NULL);
1278
                SQLITE_ANY, NULL, arr_func1[i].func, NULL, NULL);
1162
        _sqlite_error(res);
1279
        _sqlite_error(res);
1163
    }
1280
    }
1164
 
1281
 
-
 
1282
    len = sizeof(arr_func2) / sizeof(arr_func2[0]);
-
 
1283
    for (i = 0; i < len; i++) {
-
 
1284
        res = sqlite3_create_function(g_workspace, arr_func2[i].name, 2, 
-
 
1285
                SQLITE_ANY, NULL, arr_func2[i].func, NULL, NULL);
-
 
1286
        _sqlite_error(res);
-
 
1287
    }
-
 
1288
 
1165
    len = sizeof(arr_sum1) / sizeof(arr_sum1[0]);
1289
    len = sizeof(arr_sum1) / sizeof(arr_sum1[0]);
1166
    for (i = 0; i < len; i++) {
1290
    for (i = 0; i < len; i++) {
1167
        res = sqlite3_create_function(g_workspace, arr_sum1[i].name, 1, 
1291
        res = sqlite3_create_function(g_workspace, arr_sum1[i].name, 1, 
1168
                SQLITE_ANY, NULL, NULL, arr_sum1[i].func, __vecsummary_finalize);
1292
                SQLITE_ANY, NULL, NULL, arr_sum1[i].func, __vecsummary_finalize);
1169
        _sqlite_error(res);
1293
        _sqlite_error(res);