From f686298664133b455ae19b5ceadcca19abde84eb Mon Sep 17 00:00:00 2001 From: Marshall Lochbaum Date: Wed, 8 Jun 2022 18:01:27 -0400 Subject: [PATCH] =?UTF-8?q?Native=20empty=20dyadic=20Cells=20(=CB=98)?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/builtins/md1.c | 83 +++++++++++++++++++++++++++------------------- 1 file changed, 48 insertions(+), 35 deletions(-) diff --git a/src/builtins/md1.c b/src/builtins/md1.c index 4bc3d1c6..2c7d6881 100644 --- a/src/builtins/md1.c +++ b/src/builtins/md1.c @@ -414,8 +414,46 @@ static B m1c2(B t, B f, B w, B x) { // consumes w,x #pragma GCC diagnostic ignored "-Wsometimes-uninitialized" // no gcc case because gcc is gcc and does gcc things instead of doing what it's asked to do #endif - -extern B rt_cell; + +static B to_fill_cell(B x) { // consumes x + B xf = getFillQ(x); + if (noFill(xf)) xf = m_f64(0); + ur cr = rnk(x)-1; + usz *sh = a(x)->sh+1; + usz csz = 1; + for (usz i=0; i1) shcpy(csh, sh, cr); + decG(x); + return taga(ca); +} +static B merge_fill_result(B rc) { + u64 rr = isArr(rc)? rnk(rc)+1ULL : 1; + if (rr>UR_MAX) thrM("˘: Result rank too large"); + B rf = getFillQ(rc); + Arr* r = m_fillarrp(0); + fillarr_setFill(r, rf); + usz* rsh = arr_shAlloc(r, rr); + if (rr>1) { + rsh[0] = 0; + shcpy(rsh+1, a(rc)->sh, rr-1); + } + dec(rc); + return taga(r); +} +B cell2_empty(B f, B w, B x, ur wr, ur xr) { + if (!isPureFn(f) || !CATCH_ERRORS) { dec(w); dec(x); return emptyHVec(); } + if (wr) w = to_fill_cell(w); + if (xr) x = to_fill_cell(x); + if (CATCH) return emptyHVec(); + B rc = c2(f, w, x); + popCatch(); + return merge_fill_result(rc); +} + B cell_c1(Md1D* d, B x) { B f = d->f; if (isAtm(x) || rnk(x)==0) { B r = c1(f, x); @@ -427,36 +465,11 @@ B cell_c1(Md1D* d, B x) { B f = d->f; usz cam = a(x)->sh[0]; if (cam==0) { if (!isPureFn(f) || !CATCH_ERRORS) { decG(x); return emptyHVec(); } - - B xf = getFillQ(x); - if (noFill(xf)) xf = m_f64(0); - - usz csz = 1; - ur cr = rnk(x)-1; - for (usz i=0; ish[i+1])) thrF("˘: Empty argument too large (%H ≡ ≢𝕩)", x); - MAKE_MUT(fc, csz); - mut_fill(fc, 0, xf, csz); dec(xf); - Arr* ca = mut_fp(fc); - usz* csh = arr_shAlloc(ca, cr); - if (cr>1) shcpy(csh, a(x)->sh+1, cr); - decG(x); - + B cf = to_fill_cell(x); if (CATCH) return emptyHVec(); - B rc = c1(f, taga(ca)); + B rc = c1(f, cf); popCatch(); - - u64 rr = isArr(rc)? rnk(rc)+1ULL : 1; - if (rr>UR_MAX) thrM("˘: Result rank too large"); - B rf = getFillQ(rc); - Arr* r = m_fillarrp(0); - fillarr_setFill(r, rf); - usz* rsh = arr_shAlloc(r, rr); - if (rr>1) { - rsh[0] = 0; - shcpy(rsh+1, a(rc)->sh, rr-1); - } - dec(rc); - return taga(r); + return merge_fill_result(rc); } S_SLICES(x) M_HARR(r, cam); @@ -472,14 +485,16 @@ B cell_c2(Md1D* d, B w, B x) { B f = d->f; B r; if (wr==0 && xr==0) return isAtm(r = c2(f, w, x))? m_atomUnit(r) : r; if (wr==0) { - usz cam = a(x)->sh[0]; if (cam==0) goto zero; + usz cam = a(x)->sh[0]; + if (cam==0) return cell2_empty(f, w, x, wr, xr); S_SLICES(x) M_HARR(r, cam); for (usz i=0,p=0; ish[0]; if (cam==0) goto zero; + usz cam = a(w)->sh[0]; + if (cam==0) return cell2_empty(f, w, x, wr, xr); S_SLICES(w) M_HARR(r, cam); for (usz i=0,p=0; if; r = HARR_FV(r); } else { usz cam = a(w)->sh[0]; - if (cam==0) goto zero; + if (cam==0) return cell2_empty(f, w, x, wr, xr); if (cam != a(x)->sh[0]) thrF("˘: Leading axis of arguments not equal (%H ≡ ≢𝕨, %H ≡ ≢𝕩)", w, x); S_SLICES(w) S_SLICES(x) M_HARR(r, cam); @@ -496,8 +511,6 @@ B cell_c2(Md1D* d, B w, B x) { B f = d->f; r = HARR_FV(r); } return bqn_merge(r); - - zero: return m1c2(rt_cell, f, w, x); // waaaaay too complicated to handle } extern B rt_insert;