#ifdef __cplusplus extern "C" { #endif #include "EXTERN.h" #include "perl.h" #include "XSUB.h" #include "patchlevel.h" #ifdef __cplusplus } #endif #include "apse.h" #if PATCHLEVEL < 5 # define PL_na na #endif MODULE = String::Approx PACKAGE = String::Approx PROTOTYPES: DISABLE apse_t* new(CLASS, pattern, ...) char* CLASS SV* pattern CODE: apse_t* ap; apse_size_t edit_distance; IV pattern_size = sv_len(pattern); if (items == 2) edit_distance = ((pattern_size-1)/10)+1; else if (items == 3) edit_distance = (apse_size_t)SvIV(ST(2)); else { warn("Usage: new(pattern[, edit_distance])\n"); XSRETURN_UNDEF; } ap = apse_create((unsigned char *)SvPV(pattern, PL_na), pattern_size, edit_distance); if (ap) { RETVAL = ap; } else { warn("unable to allocate"); XSRETURN_UNDEF; } OUTPUT: RETVAL void DESTROY(ap) apse_t* ap CODE: apse_destroy(ap); apse_bool_t match(ap, text) apse_t* ap SV* text CODE: RETVAL = apse_match(ap, (unsigned char *)SvPV(text, PL_na), sv_len(text)); OUTPUT: RETVAL apse_bool_t match_next(ap, text) apse_t* ap SV* text CODE: RETVAL = apse_match_next(ap, (unsigned char *)SvPV(text, PL_na), sv_len(text)); OUTPUT: RETVAL apse_ssize_t index(ap, text) apse_t* ap SV* text CODE: RETVAL = apse_index(ap, (unsigned char *)SvPV(text, PL_na), sv_len(text)); OUTPUT: RETVAL void slice(ap, text) apse_t* ap SV* text PREINIT: apse_size_t match_begin; apse_size_t match_size; PPCODE: if (ap->use_minimal_distance) { apse_slice(ap, (unsigned char *)SvPV(text, PL_na), (apse_size_t)sv_len(text), &match_begin, &match_size); EXTEND(sp, 3); PUSHs(sv_2mortal(newSViv(match_begin))); PUSHs(sv_2mortal(newSViv(match_size))); PUSHs(sv_2mortal(newSViv(ap->edit_distance))); } else if (apse_slice(ap, (unsigned char *)SvPV(text, PL_na), (apse_size_t)sv_len(text), &match_begin, &match_size)) { EXTEND(sp, 2); PUSHs(sv_2mortal(newSViv(match_begin))); PUSHs(sv_2mortal(newSViv(match_size))); } void slice_next(ap, text) apse_t* ap SV* text PREINIT: apse_size_t match_begin; apse_size_t match_size; PPCODE: if (apse_slice_next(ap, (unsigned char *)SvPV(text, PL_na), sv_len(text), &match_begin, &match_size)) { EXTEND(sp, 2); PUSHs(sv_2mortal(newSViv(match_begin))); PUSHs(sv_2mortal(newSViv(match_size))); if (ap->use_minimal_distance) { EXTEND(sp, 1); PUSHs(sv_2mortal(newSViv(ap->edit_distance))); } } void set_greedy(ap) apse_t* ap CODE: apse_set_greedy(ap, 1); apse_bool_t set_caseignore_slice(ap, ...) apse_t* ap PREINIT: apse_size_t offset; apse_size_t size; apse_bool_t ignore; CODE: offset = items < 2 ? 0 : (apse_size_t)SvIV(ST(1)); size = items < 3 ? ap->pattern_size : (apse_size_t)SvIV(ST(2)); ignore = items < 4 ? 1 : (apse_bool_t)SvIV(ST(3)); RETVAL = apse_set_caseignore_slice(ap, offset, size, ignore); OUTPUT: RETVAL apse_bool_t set_insertions(ap, insertions) apse_t* ap apse_size_t insertions = SvUV($arg); CODE: RETVAL = apse_set_insertions(ap, insertions); OUTPUT: RETVAL apse_bool_t set_deletions(ap, deletions) apse_t* ap apse_size_t deletions = SvUV($arg); CODE: RETVAL = apse_set_deletions(ap, deletions); OUTPUT: RETVAL apse_bool_t set_substitutions(ap, substitutions) apse_t* ap apse_size_t substitutions = SvUV($arg); CODE: RETVAL = apse_set_substitutions(ap, substitutions); OUTPUT: RETVAL apse_bool_t set_edit_distance(ap, edit_distance) apse_t* ap apse_size_t edit_distance = SvUV($arg); CODE: RETVAL = apse_set_edit_distance(ap, edit_distance); OUTPUT: RETVAL apse_size_t get_edit_distance(ap) apse_t* ap CODE: ST(0) = sv_newmortal(); sv_setiv(ST(0), apse_get_edit_distance(ap)); apse_bool_t set_text_initial_position(ap, text_initial_position) apse_t* ap apse_size_t text_initial_position = SvUV($arg); CODE: RETVAL = apse_set_text_initial_position(ap, text_initial_position); OUTPUT: RETVAL apse_bool_t set_text_final_position(ap, text_final_position) apse_t* ap apse_size_t text_final_position = SvUV($arg); CODE: RETVAL = apse_set_text_final_position(ap, text_final_position); OUTPUT: RETVAL apse_bool_t set_text_position_range(ap, text_position_range) apse_t* ap apse_size_t text_position_range = SvUV($arg); CODE: RETVAL = apse_set_text_position_range(ap, text_position_range); OUTPUT: RETVAL void set_minimal_distance(ap, b) apse_t* ap apse_bool_t b CODE: apse_set_minimal_distance(ap, b);