Skip to content

Commit

Permalink
structural ⍢, (f⍤g)A
Browse files Browse the repository at this point in the history
  • Loading branch information
dzaima committed Mar 1, 2020
1 parent 253274a commit 0eb16c2
Show file tree
Hide file tree
Showing 30 changed files with 324 additions and 27 deletions.
7 changes: 5 additions & 2 deletions src/APL/Indexer.java
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,10 @@ public Indexer(int[] sh, int IO) {
}
}

public int pos() {
return ci-1;
}

public boolean hasNext() {
return ci < ia;
}
Expand Down Expand Up @@ -110,7 +114,7 @@ public static double[][] inds(Obj ov) { // ⎕VI←1 indexes to double[][]
}
private static final int[] i1 = new int[1];
private static final int[] i0 = new int[0];
public static final int[] indsh(Obj ov) { // must be called after inds(ov)
public static int[] indsh(Obj ov) { // must be called after inds(ov)
Value v = (Value) ov;
if (v instanceof Primitive) return i1;
if (v.ia == 0) return i0;
Expand All @@ -119,7 +123,6 @@ public static final int[] indsh(Obj ov) { // must be called after inds(ov)
return fst.shape;
}

@SuppressWarnings("NullableProblems") // not using @NotNull for non-intelliJ compilers
public Iterator<int[]> iterator() {
return this;
}
Expand Down
6 changes: 6 additions & 0 deletions src/APL/types/Fun.java
Original file line number Diff line number Diff line change
Expand Up @@ -34,6 +34,12 @@ public Obj callInvA(Value a, Value w) {
throw new DomainError(this+" doesn't support dyadic inverting of ⍺", this, w);
}

public boolean strInv() { return false; } // can assume that this Fun has been called before of what's to be inverted
public boolean strInvW() { return false; }

public Value strInv(Value w, Value origW) { throw new IllegalStateException("calling unsupported strInv(w, origW)"); }
public Value strInvW(Value a, Value w, Value origW) { throw new IllegalStateException("calling unsupported strInvW(a, w, origW)"); }

public interface NumMV {
Value call(Num w);
default boolean retNum() {
Expand Down
2 changes: 1 addition & 1 deletion src/APL/types/Num.java
Original file line number Diff line number Diff line change
Expand Up @@ -220,7 +220,7 @@ public Value safePrototype() {
}

@Override
public Value[] values() {
public Value[] valuesCopy() {
return new Value[]{this};
}

Expand Down
5 changes: 4 additions & 1 deletion src/APL/types/Value.java
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,7 @@ public abstract class Value extends Obj implements Iterable<Value> {
this.rank = rank;
}
public int[] asIntVec() { // succeeds on rank ≤ 1
RankError.must(rank<=1, "using rank "+rank+" array as vector");
RankError.must(rank<=1, "using rank "+rank+" array as an integer vector");
return asIntArr();
}
public abstract int[] asIntArr();
Expand Down Expand Up @@ -118,6 +118,9 @@ public String oneliner() {


public Value[] values() {
return valuesCopy();
}
public Value[] valuesCopy() {
Value[] vs = new Value[ia];
for (int i = 0; i < ia; i++) vs[i] = get(i);
return vs;
Expand Down
2 changes: 1 addition & 1 deletion src/APL/types/arrs/DoubleArr.java
Original file line number Diff line number Diff line change
Expand Up @@ -128,7 +128,7 @@ public Value squeeze() {
}

@Override
public Value[] values() {
public Value[] valuesCopy() {
Value[] vs = new Value[ia];
for (int i = 0; i < ia; i++) vs[i] = new Num(arr[i]);
return vs;
Expand Down
4 changes: 2 additions & 2 deletions src/APL/types/arrs/EmptyArr.java
Original file line number Diff line number Diff line change
Expand Up @@ -52,8 +52,8 @@ public Value ofShape(int[] sh) {

private static final Value[] NO_VALUES = new Value[0];
@Override
public Value[] values() {
return NO_VALUES;
public Value[] valuesCopy() {
return NO_VALUES; // safe, copy or not - doesn't matter
}

@Override
Expand Down
4 changes: 3 additions & 1 deletion src/APL/types/arrs/HArr.java
Original file line number Diff line number Diff line change
Expand Up @@ -70,10 +70,12 @@ public Value safePrototype() {
if (ia == 0) return null;
return arr[0].safePrototype();
}
@Override
public Value[] values() {
return arr;
}
public Value[] valuesCopy() {
return arr.clone();
}
public Value ofShape(int[] sh) {
assert ia == Arr.prod(sh);
return new HArr(arr, sh);
Expand Down
2 changes: 1 addition & 1 deletion src/APL/types/arrs/Rank0Arr.java
Original file line number Diff line number Diff line change
Expand Up @@ -48,7 +48,7 @@ public Value ofShape(int[] sh) {
}

@Override
public Value[] values() {
public Value[] valuesCopy() {
return new Value[]{item};
}
}
2 changes: 1 addition & 1 deletion src/APL/types/arrs/Shape1Arr.java
Original file line number Diff line number Diff line change
Expand Up @@ -48,7 +48,7 @@ public Value ofShape(int[] sh) {
}

@Override
public Value[] values() {
public Value[] valuesCopy() {
return new Value[]{item};
}

Expand Down
2 changes: 1 addition & 1 deletion src/APL/types/arrs/SingleItemArr.java
Original file line number Diff line number Diff line change
Expand Up @@ -58,7 +58,7 @@ public Value ofShape(int[] sh) {
public boolean quickDoubleArr() {
return item instanceof Num;
}
public Value[] values() {
public Value[] valuesCopy() {
Value[] vs = new Value[ia];
for (int i = 0; i < ia; i++) vs[i] = item;
return vs;
Expand Down
6 changes: 6 additions & 0 deletions src/APL/types/functions/DerivedDop.java
Original file line number Diff line number Diff line change
Expand Up @@ -32,4 +32,10 @@ public Obj call(Value a, Value w) {
if (!(ww instanceof Arr) && wws.length() != 1) wws = "("+wws+")";
return aa.toString()+op.repr()+wws;
}

public boolean strInv() { return op.strInv(aa, ww); }
public boolean strInvW() { return op.strInvW(aa, ww); }

public Value strInv(Value w, Value origW) { return op.strInv(aa, ww, w, origW); }
public Value strInvW(Value a, Value w, Value origW) { return op.strInvW(aa, ww, a, w, origW); }
}
6 changes: 6 additions & 0 deletions src/APL/types/functions/DerivedMop.java
Original file line number Diff line number Diff line change
Expand Up @@ -30,4 +30,10 @@ public Obj call(Value a, Value w) {
@Override public String repr() {
return aa.toString()+op.repr();
}

public boolean strInv() { return op.strInv(aa); }
public boolean strInvW() { return op.strInvW(aa); }

public Value strInv(Value w, Value origW) { return op.strInv(aa, w, origW); }
public Value strInvW(Value a, Value w, Value origW) { return op.strInvW(aa, a, w, origW); }
}
4 changes: 4 additions & 0 deletions src/APL/types/functions/Dop.java
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,10 @@ public Obj callInvW(Obj aa, Obj ww, Value a, Value w) {
public Obj callInvA(Obj aa, Obj ww, Value a, Value w) {
throw new DomainError(this+" doesn't support dyadic inverting of ⍺", this, w);
}
public boolean strInv(Obj aa, Obj ww) { return false; }
public boolean strInvW(Obj aa, Obj ww) { return false; }
public Value strInv(Obj aa, Obj ww, Value w, Value origW) { throw new IllegalStateException("calling unsupported dop.strInv(w, origW)"); }
public Value strInvW(Obj aa, Obj ww, Value a, Value w, Value origW) { throw new IllegalStateException("calling unsupported dop.strInvW(a, w, origW)"); }

public String toString() {
return repr();
Expand Down
4 changes: 4 additions & 0 deletions src/APL/types/functions/Mop.java
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,10 @@ public Obj callInvW(Obj f, Value a, Value w) {
public Obj callInvA(Obj f, Value a, Value w) {
throw new DomainError(this+" doesn't support dyadic inverting of ⍺", this, w);
}
public boolean strInv(Obj f) { return false; }
public boolean strInvW(Obj f) { return false; }
public Value strInv(Obj f, Value w, Value origW) { throw new IllegalStateException("calling unsupported mop.strInv(w, origW)"); }
public Value strInvW(Obj f, Value a, Value w, Value origW) { throw new IllegalStateException("calling unsupported mop.strInvW(a, w, origW)"); }

public String toString() {
return repr();
Expand Down
10 changes: 7 additions & 3 deletions src/APL/types/functions/builtins/dops/AtBuiltin.java
Original file line number Diff line number Diff line change
Expand Up @@ -14,8 +14,12 @@ public class AtBuiltin extends Dop {
public AtBuiltin(Scope sc) {
super(sc);
}
public Obj call(Obj aa, Obj ww, Value w, DerivedDop derv) {
int IO = sc.IO;

public Obj at(Obj aa, Obj ww, Value w, DerivedDop derv) {
return at(aa, ww, w, sc.IO);
}

public static Value at(Obj aa, Obj ww, Value w, int IO) {
int ia = w.ia;
if (ww instanceof Fun) {
Value vba = (Value) ((Fun) ww).call(w);
Expand Down Expand Up @@ -74,7 +78,7 @@ public Obj call(Obj aa, Obj ww, Value w, DerivedDop derv) {
for (int i = 0; i < matchingCount; i++) {
ra[indexes[i]] = replacement[i];
}
return Arr.create(ra, w.shape);
return Arr.createL(ra, w.shape);
} else {
for (int i = 0; i < matchingCount; i++) {
indexes[i] = Indexer.ind(w.shape, wwd, i, IO);
Expand Down
25 changes: 21 additions & 4 deletions src/APL/types/functions/builtins/dops/DualBuiltin.java
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
package APL.types.functions.builtins.dops;

import APL.errors.SyntaxError;
import APL.types.*;
import APL.types.functions.*;

Expand All @@ -11,14 +12,30 @@ public class DualBuiltin extends Dop {


public Obj call(Obj aa, Obj ww, Value w, DerivedDop derv) {
isFn(aa, '⍶'); isFn(ww, '⍹');
isFn(ww, '⍹');
Fun under = (Fun) ww;
return under.callInv( (Value) ((Fun)aa).call((Value) under.call(w)));
Value sub = (Value) under.call(w);
if (under.strInv()) {
Value obj = aa instanceof Value? (Value) aa : (Value) ((Fun) aa).call(sub);
return under.strInv(obj, w);
}

if (!(aa instanceof Fun)) throw new SyntaxError("⍶ of computational ⍢ must be a function");
Value obj = (Value) ((Fun) aa).call(sub);
return under.callInv(obj);
}
public Obj callInv(Obj aa, Obj ww, Value w) {
isFn(aa, '⍶'); isFn(ww, '⍹');
isFn(ww, '⍹');
Fun under = (Fun) ww;
return under.callInv( (Value) ((Fun)aa).callInv((Value) under.call(w)));
Value sub = (Value) under.call(w);
if (under.strInv()) {
Value obj = aa instanceof Value? (Value) aa : (Value) ((Fun) aa).callInv(sub);
return under.strInv(obj, w);
}

if (!(aa instanceof Fun)) throw new SyntaxError("⍶ of computational ⍢ must be a function");
Value obj = (Value) ((Fun) aa).callInv(sub);
return under.callInv(obj);
}

public Obj call(Obj aa, Obj ww, Value a, Value w, DerivedDop derv) {
Expand Down
15 changes: 15 additions & 0 deletions src/APL/types/functions/builtins/dops/JotBuiltin.java
Original file line number Diff line number Diff line change
Expand Up @@ -43,4 +43,19 @@ public Obj call(Obj aa, Obj ww, Value a, Value w, DerivedDop derv) {
}
return ((Fun)aa).call(a, (Value)((Fun)ww).call(w));
}
public boolean strInv(Obj aa, Obj ww) {
if (!(ww instanceof Fun)) return false;
Fun wwf = (Fun) ww;
return aa instanceof Fun? ((Fun) aa).strInv() && wwf.strInv() : wwf.strInvW();
}
public Value strInv(Obj aa, Obj ww, Value w, Value origW) {
Fun wwf = (Fun) ww;
if (aa instanceof Fun) {
Fun aaf = (Fun) aa;
Value gI = aaf.strInv(w, (Value) wwf.call(origW));
return wwf.strInv(gI, origW);
} else {
return wwf.strInvW((Value) aa, w, origW);
}
}
}
13 changes: 12 additions & 1 deletion src/APL/types/functions/builtins/dops/JotDiaeresisBuiltin.java
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
package APL.types.functions.builtins.dops;

import APL.errors.SyntaxError;
import APL.types.*;
import APL.types.functions.*;

Expand All @@ -15,4 +16,14 @@ public Obj call(Obj aa, Obj ww, Value a, Value w, DerivedDop derv) {
isFn(aa, '⍶'); isFn(ww, '⍹');
return ((Fun) aa).call((Value) ((Fun) ww).call(a, w));
}
}

public Obj call(Obj aa, Obj ww, Value w, DerivedDop derv) {
isFn(aa, '⍶'); isFn(ww, '⍹');
return ((Fun) aa).call((Value) ((Fun) ww).call(w));
}

public Obj callInv(Obj aa, Obj ww, Value w) {
isFn(aa, '⍶'); isFn(ww, '⍹');
return ((Fun) aa).call((Value) ((Fun) ww).call(w));
}
}
18 changes: 18 additions & 0 deletions src/APL/types/functions/builtins/dops/RepeatBuiltin.java
Original file line number Diff line number Diff line change
Expand Up @@ -102,4 +102,22 @@ public Obj callInvA(Obj aa, Obj ww, Value a, Value w) {

throw new DomainError("inverting ⍺ of f⍣C is only possible when C∊¯1 1");
}

public boolean strInv(Obj aa, Obj ww) {
return aa instanceof Fun && ((Fun) aa).strInv() && ww instanceof Num;
}
public Value strInv(Obj aa, Obj ww, Value w, Value origW) {
int n = ((Num) ww).asInt();
Value[] origs = new Value[n];
Value corig = origW;
for (int i = 0; i < n; i++) {
origs[i] = corig;
corig = (Value) ((Fun) aa).call(corig);
}
Value c = w;
for (int i = n-1; i >= 0; i--) {
c = ((Fun) aa).strInv(c, origs[i]);
}
return c;
}
}
7 changes: 7 additions & 0 deletions src/APL/types/functions/builtins/fns/CatBuiltin.java
Original file line number Diff line number Diff line change
Expand Up @@ -100,4 +100,11 @@ private static void copyChunksD(boolean scalar, double[] av, double[] rv, int of
}
}



public boolean strInv() { return true; }
public Value strInv(Value w, Value origW) {
if (w.ia != origW.ia) throw new DomainError("⍢, expected equal amount of output & output items", this);
return w.ofShape(origW.shape);
}
}
12 changes: 11 additions & 1 deletion src/APL/types/functions/builtins/fns/DownArrowBuiltin.java
Original file line number Diff line number Diff line change
Expand Up @@ -50,7 +50,7 @@ public Obj call(Value w) {
return new HArr(res, nsh);
}

public Obj call(Value a, Value w) { // FIXME ⍴⍴⍺ < ⍴⍴⍵
public Obj call(Value a, Value w) { // TODO ⍴⍺ < ⍴⍴⍵
int IO = sc.IO;
int[] shape = a.asIntVec();
if (shape.length == 0) return w;
Expand All @@ -76,4 +76,14 @@ public Obj call(Value a, Value w) { // FIXME ⍴⍴⍺ < ⍴⍴⍵
}
return Arr.create(arr, shape);
}

public boolean strInvW() { return true; }
public Value strInvW(Value a, Value w, Value origW) {
int[] ls = a.asIntVec();
int[] sh = origW.shape;
for (int i = 0; i < ls.length; i++) {
ls[i] = ls[i]>0? ls[i]-sh[i] : ls[i]+sh[i];
}
return UpArrowBuiltin.strInv(ls, w, origW);
}
}
25 changes: 25 additions & 0 deletions src/APL/types/functions/builtins/fns/EpsilonBuiltin.java
Original file line number Diff line number Diff line change
@@ -1,5 +1,7 @@
package APL.types.functions.builtins.fns;

import APL.Main;
import APL.errors.DomainError;
import APL.types.*;
import APL.types.functions.Builtin;

Expand Down Expand Up @@ -51,4 +53,27 @@ public Obj call(Value a, Value w) {
}
return Arr.create(res, a.shape);
}


public boolean strInv() { return true; }
public Value strInv(Value w, Value origW) {
Value[] vs = w.values();
Value[] res = new Value[origW.ia];
int e = copyIn(res, vs, origW, 0);
if (e != w.ia) throw new DomainError("⍢∊ expected equal amount of output & output items", this);
return Arr.create(res, origW.shape);
}
private int copyIn(Value[] res, Value[] vs, Value orig, int s) {
for (int i = 0; i < orig.ia; i++) {
Value origN = orig.get(i);
if (origN instanceof Primitive) {
res[i] = vs[s++];
} else {
Value[] resN = new Value[origN.ia];
s = copyIn(resN, vs, origN, s);
res[i] = Arr.create(resN, origN.shape);
}
}
return s;
}
}

0 comments on commit 0eb16c2

Please sign in to comment.