Perl bindings for Clownfish::StringIterator
Project: http://git-wip-us.apache.org/repos/asf/lucy-clownfish/repo Commit: http://git-wip-us.apache.org/repos/asf/lucy-clownfish/commit/693cff8b Tree: http://git-wip-us.apache.org/repos/asf/lucy-clownfish/tree/693cff8b Diff: http://git-wip-us.apache.org/repos/asf/lucy-clownfish/diff/693cff8b Branch: refs/heads/master Commit: 693cff8b57b22ad46b72b9dbb7bf3ea5f8a05347 Parents: 5583961 Author: Nick Wellnhofer <wellnho...@aevum.de> Authored: Sun Nov 15 18:00:06 2015 +0100 Committer: Nick Wellnhofer <wellnho...@aevum.de> Committed: Tue Nov 17 19:08:43 2015 +0100 ---------------------------------------------------------------------- runtime/core/Clownfish/String.cfh | 4 + .../perl/buildlib/Clownfish/Build/Binding.pm | 95 ++++++++++++++++++++ 2 files changed, 99 insertions(+) ---------------------------------------------------------------------- http://git-wip-us.apache.org/repos/asf/lucy-clownfish/blob/693cff8b/runtime/core/Clownfish/String.cfh ---------------------------------------------------------------------- diff --git a/runtime/core/Clownfish/String.cfh b/runtime/core/Clownfish/String.cfh index a2d6337..aa415a2 100644 --- a/runtime/core/Clownfish/String.cfh +++ b/runtime/core/Clownfish/String.cfh @@ -285,6 +285,10 @@ public final class Clownfish::String nickname Str Tail(String *self); } +/** + * Iterate Unicode code points in a String. + */ + public final class Clownfish::StringIterator nickname StrIter inherits Clownfish::Obj { http://git-wip-us.apache.org/repos/asf/lucy-clownfish/blob/693cff8b/runtime/perl/buildlib/Clownfish/Build/Binding.pm ---------------------------------------------------------------------- diff --git a/runtime/perl/buildlib/Clownfish/Build/Binding.pm b/runtime/perl/buildlib/Clownfish/Build/Binding.pm index ecb6bba..d8cc8b2 100644 --- a/runtime/perl/buildlib/Clownfish/Build/Binding.pm +++ b/runtime/perl/buildlib/Clownfish/Build/Binding.pm @@ -29,6 +29,7 @@ sub bind_all { $class->bind_bytebuf; $class->bind_charbuf; $class->bind_string; + $class->bind_stringiterator; $class->bind_err; $class->bind_hash; $class->bind_hashiterator; @@ -280,6 +281,100 @@ END_XS_CODE Clownfish::CFC::Binding::Perl::Class->register($binding); } +sub bind_stringiterator { + my @hand_rolled = qw( + Next + Prev + ); + + my $pod_spec = Clownfish::CFC::Binding::Perl::Pod->new; + my $synopsis = <<'END_SYNOPSIS'; + my $iter = $string->top; + while (my $code_point = $iter->next) { + ... + } +END_SYNOPSIS + my $next_pod = <<'END_POD'; +=head2 next() + +Return the code point after the current position and advance the +iterator. Returns undef at the end of the string. Returns zero +but true for U+0000. +END_POD + my $prev_pod = <<'END_POD'; +=head2 prev() + +Return the code point before the current position and go one step back. +Returns undef at the start of the string. Returns zero but true for +U+0000. +END_POD + $pod_spec->set_synopsis($synopsis); + $pod_spec->add_method( + method => 'Next', + alias => 'next', + pod => $next_pod, + ); + $pod_spec->add_method( + method => 'Prev', + alias => 'prev', + pod => $prev_pod, + ); + + my $xs_code = <<'END_XS_CODE'; +MODULE = Clownfish PACKAGE = Clownfish::StringIterator + +SV* +next(self) + cfish_StringIterator *self; +CODE: +{ + int32_t cp = CFISH_StrIter_Next(self); + + if (cp == CFISH_STR_OOB) { + RETVAL = &PL_sv_undef; + } + else if (cp == 0) { + /* Zero but true. */ + RETVAL = newSVpvn("0e0", 3); + } + else { + RETVAL = newSViv(cp); + } +} +OUTPUT: RETVAL + +SV* +prev(self) + cfish_StringIterator *self; +CODE: +{ + int32_t cp = CFISH_StrIter_Prev(self); + + if (cp == CFISH_STR_OOB) { + RETVAL = &PL_sv_undef; + } + else if (cp == 0) { + /* Zero but true. */ + RETVAL = newSVpvn("0e0", 3); + } + else { + RETVAL = newSViv(cp); + } +} +OUTPUT: RETVAL +END_XS_CODE + + my $binding = Clownfish::CFC::Binding::Perl::Class->new( + parcel => "Clownfish", + class_name => "Clownfish::StringIterator", + ); + $binding->set_pod_spec($pod_spec); + $binding->exclude_method($_) for @hand_rolled; + $binding->append_xs($xs_code); + + Clownfish::CFC::Binding::Perl::Class->register($binding); +} + sub bind_err { my $pod_spec = Clownfish::CFC::Binding::Perl::Pod->new; my $synopsis = <<'END_SYNOPSIS';