Skip to content

Commit

Permalink
Browse files Browse the repository at this point in the history
Implement Z, Zop, X, Xop
  • Loading branch information
sorear committed Feb 12, 2011
1 parent b86e304 commit f3b81bb
Show file tree
Hide file tree
Showing 5 changed files with 137 additions and 10 deletions.
119 changes: 113 additions & 6 deletions lib/Builtins.cs
Expand Up @@ -471,12 +471,91 @@ class BatchSource: ItemSource {
}
}

//class ZipSource : ItemSource {
// VarDeque[] sources;
// public ZipSource(VarDeque[] sources) {
// ...
// }
//}
class ZipSource : ItemSource {
VarDeque[] sources;
public ZipSource(Variable[] pcl) {
sources = new VarDeque[pcl.Length];
for (int i = 0; i < pcl.Length; i++)
sources[i] = new VarDeque(pcl[i]);
}

public override bool TryGet(out Variable[] r, bool block) {
r = null;
for (int i = 0; i < sources.Length; i++)
switch (TryOne(sources[i], block)) {
case -1: return true;
case 0: return false;
}
r = new Variable[sources.Length];
for (int i = 0; i < sources.Length; i++)
r[i] = sources[i].Shift();
return true;
}
}

class CrossSource: ItemSource {
VarDeque[] basic;
VarDeque[] iter;
Variable[] basic_top;
Variable[] iter_top;
// 0=init 1=end i=advance wheel i-2
int state;

public CrossSource(Variable[] pcl) {
basic = new VarDeque[pcl.Length];
iter = new VarDeque[pcl.Length];
basic_top = new Variable[pcl.Length];
iter_top = new Variable[pcl.Length];
for (int i = 0; i < pcl.Length; i++) {
iter[i] = new VarDeque(pcl[i]);
}
}

public override bool TryGet(out Variable[] r, bool block) {
r = null;
if (state == 0) {
// Make sure all the lists are non-empty.
for (int i = 0; i < iter.Length; i++) {
switch (TryOne(iter[i], block)) {
case -1: return true;
case 0: return false;
case 1: break;
}
}
for (int i = 0; i < iter.Length; i++) {
iter_top[i] = iter[i].Shift();
if (i != 0) {
basic[i] = new VarDeque(iter[i]);
basic_top[i] = iter_top[i];
}
}
}
else if (state == 1) {
return true;
}
else {
again:
int wheel = state - 2;
switch (TryOne(iter[wheel], block)) {
case 0: return false;
case +1:
iter_top[wheel] = iter[wheel].Shift();
break;
case -1:
if (wheel == 0) return true;
iter[wheel] = new VarDeque(basic[wheel]);
iter_top[wheel] = basic_top[wheel];
state--;
goto again;
}
}
r = new Variable[iter_top.Length];
for (int i = 0; i < iter_top.Length; i++)
r[i] = iter_top[i];
state = iter_top.Length + 1;
return true;
}
}

private static SubInfo CommonMEMap_I = new SubInfo("KERNEL map", null,
CommonMEMap_C, null, null, new int[] {
Expand Down Expand Up @@ -546,6 +625,7 @@ class BatchSource: ItemSource {
return Kernel.Die(th, "Invalid IP");
}
}

public static Frame MEMap(Frame th, Variable[] lst) {
VarDeque iter = new VarDeque(lst);
Variable fcn = iter.Shift();
Expand All @@ -560,6 +640,33 @@ class BatchSource: ItemSource {
return fr;
}

static IP6 ExtractWith(bool with, ref Variable[] pcl) {
if (!with) return null;
Variable[] opcl = pcl;
pcl = new Variable[pcl.Length - 1];
for (int j = 0; j < pcl.Length; j++)
pcl[j] = opcl[j+1];
return opcl[0].Fetch();
}

public static Frame MEZip(Frame th, bool with, Variable[] pcl) {
Frame fr = th.MakeChild(null, CommonMEMap_I);
fr.lexi0 = 0;
fr.lex2 = ExtractWith(with, ref pcl);
fr.lex0 = new ZipSource(pcl);
fr.lex1 = new VarDeque();
return fr;
}

public static Frame MECross(Frame th, bool with, Variable[] pcl) {
Frame fr = th.MakeChild(null, CommonMEMap_I);
fr.lexi0 = 0;
fr.lex2 = ExtractWith(with, ref pcl);
fr.lex0 = new CrossSource(pcl);
fr.lex1 = new VarDeque();
return fr;
}

private static SubInfo CommonGrep_I = new SubInfo("KERNEL grep", null,
CommonGrep_C, null, null, new int[] {
2, 3, SubInfo.ON_NEXT, 0, 0,
Expand Down
2 changes: 2 additions & 0 deletions lib/CLRBackend.cs
Expand Up @@ -3118,6 +3118,8 @@ class NamProcessor {
thandlers["bif_at_pos"] = thandlers["obj_at_pos"] = Contexty("mro_at_pos");
thandlers["bif_exists_key"] = thandlers["obj_exists_key"] = Contexty("mro_exists_key");
thandlers["bif_delete_key"] = thandlers["obj_delete_key"] = Contexty("mro_delete_key");
thandlers["bif_cross"] = Methody(Tokens.Variable, Tokens.Builtins.GetMethod("MECross"));
thandlers["bif_zip"] = Methody(Tokens.Variable, Tokens.Builtins.GetMethod("MEZip"));
thandlers["obj_typename"] = Methody(null, Tokens.IP6.GetMethod("GetTypeName"));
thandlers["fetch"] = Methody(null, Tokens.Variable_Fetch);
thandlers["bget"] = FieldGet(Tokens.BValue, "v");
Expand Down
17 changes: 13 additions & 4 deletions lib/SAFE.setting
Expand Up @@ -804,6 +804,19 @@ sub sort(*@bits) { @bits.sort }
sub _array_constructor(\$parcel) { _array_constructor($parcel) }
sub _hash_constructor(\$parcel) { my $r := (anon %hash = $parcel); $r }
sub infix:<Z>(\|$pcl) {
Q:CgOp { (bif_zip (b 0) (unbox fvarlist (@ {$pcl}))) }
}
sub infix:<X>(\|$pcl) {
Q:CgOp { (bif_cross (b 0) (unbox fvarlist (@ {$pcl}))) }
}
sub zipop(\|$pcl) {
Q:CgOp { (bif_zip (b 1) (unbox fvarlist (@ {$pcl}))) }
}
sub crossop(\|$pcl) {
Q:CgOp { (bif_cross (b 1) (unbox fvarlist (@ {$pcl}))) }
}
# }}}
# Regular expression support {{{
my class Cursor {
Expand Down Expand Up @@ -1041,10 +1054,6 @@ sub infix:<^> (\|$args) { die "Junctions NYI" } #OK
sub prefix:<sleep> ($x) { die "Asynchronous programming NYI" } #OK
sub infix:<does> ($obj, \$roles) { die "Retyping NYI" } #OK
sub infix:<=:=> (\$a, \$b) { die "Binding checks NYI" } #OK
sub infix:<X> (\|$args) { die "Cross products NYI" } #OK
sub crossop($op) { die "Cross products NYI" } #OK
sub infix:<Z> (\|$args) { die "Zip operators NYI" } #OK
sub zipop($op) { die "Zip operators NYI" } #OK
sub infix:<minmax>(\|$args) { die "minmax NYI" } #OK
sub infix:<...>(\|$args) { die "Series op NYI" } #OK
sub infix:<...^>(\|$args) { die "Series op NYI" } #OK
Expand Down
2 changes: 2 additions & 0 deletions src/niecza
Expand Up @@ -220,6 +220,8 @@ class Labelled is Op {
}

augment class CgOp { #OK exist
method bif_zip($fcn,$pcl) { self._cgop("bif_zip",$fcn,$pcl) }
method bif_cross($fcn,$pcl) { self._cgop("bif_cross",$fcn,$pcl) }
method double($x) {
# Hack - prevent JSON syntax errors
my $str = ~$x;
Expand Down
7 changes: 7 additions & 0 deletions test2.pl
Expand Up @@ -120,6 +120,13 @@
is +@a, 3, "capturing matches return catures in list context";
}

{
is ~[4,0 Z+ 2,0 Z+ 1,0], "7 0", "Z+ works";
is ~[1,2 X+ 3,4 X+ 5,6], "9 10 10 11 10 11 11 12", "X+ works";
is ~[4,0 Z 2,0 Z 1,0], "4 2 1 0 0 0", "Z works";
is ~[1,2 X 3,4 X 5,6], "1 3 5 1 3 6 1 4 5 1 4 6 2 3 5 2 3 6 2 4 5 2 4 6", "X works";
}

#is $?FILE, 'test.pl', '$?FILE works';
#is $?ORIG.substr(0,5), '# vim', '$?ORIG works';

Expand Down

0 comments on commit f3b81bb

Please sign in to comment.