1- /* Copyright 1990-2007, Jsoftware Inc. All rights reserved. */
2- /* Licensed use only. Any other use is in violation of copyright. */
3- /* */
4- /* Verbs: Take and Drop */
51
6- #include "j.h"
2+ #include < algorithm>
3+ #include < iterator>
4+
5+ #include " array.hpp"
6+
7+ /* * @file */
78
89A
910jtbehead (J jt, A w) {
@@ -42,12 +43,11 @@ jttk0(J jt, B b, A a, A w) {
4243 return z;
4344}
4445
45- static A
46- jttks (J jt , A a , A w ) {
46+ static array
47+ jttks (J jt, array a, array w) { // take_sparse
4748 PROLOG (0092 );
48- A a1 , q , x , y , z ;
49- B b , c ;
50- I an , m , r , * s , * u , * v ;
49+ array x, y, z;
50+ I an, r, *s, *u, *v;
5151 P *wp, *zp;
5252 an = AN (a);
5353 u = AV (a);
@@ -57,31 +57,37 @@ jttks(J jt, A a, A w) {
5757 v = AS (z);
5858 DO (an, v[i] = ABS (u[i]););
5959 zp = PAV (z);
60- wp = PAV (w );
60+ wp = PAV (w); // pointer to array values
61+
6162 if (an <= r) {
6263 RZ (a = vec (INT, r, s));
6364 MCISH (AV (a), u, an);
6465 } // vec is not virtual
65- a1 = SPA (wp , a );
66- RZ (q = jtpaxis (jt , r , a1 ));
67- m = AN (a1 );
66+
67+ auto [m, q] = [&] {
68+ array const a1 = SPA (wp, a);
69+ return std::pair{AN (a1), jtpaxis (jt, r, a1)};
70+ } ();
71+
6872 RZ (a = jtfrom (jt, q, a));
6973 u = AV (a);
7074 RZ (y = jtfrom (jt, q, shape (jt, w)));
7175 s = AV (y);
72- b = 0 ;
73- DO ( r - m , if ( b = u [ i + m ] != s [ i + m ]) break ;);
74- c = 0 ;
75- DO ( m , if ( c = u [ i ] != s [ i ]) break ;);
76+
77+ // TODO: rename b when we figure out what it is doing
78+ auto const b = std::mismatch (u + m, u + r, s + m). first != u + r;
79+
7680 if (b) {
7781 jt->fill = SPA (wp, e);
78- x = irs2 (vec (INT , r - m , m + u ), SPA (wp , x ), 0L , 1L , -1L , jttake );
82+ x = irs2 (vec (INT, r - m, m + u), SPA (wp, x), 0L , 1L , -1L , reinterpret_cast <AF>( jttake) );
7983 jt->fill = 0 ;
8084 RZ (x);
8185 } // fill cannot be virtual
8286 else
8387 x = SPA (wp, x);
84- if (c ) {
88+
89+ // TODO: rename b when we figure out what it is doing
90+ if (auto const c = std::mismatch (u, u + m, s).first != u + m; c) {
8591 A j;
8692 C *xv, *yv;
8793 I d, i, *iv, *jv, k, n, t;
@@ -97,12 +103,22 @@ jttks(J jt, A a, A w) {
97103 yv = CAV (y);
98104 xv = CAV (x);
99105 for (i = 0 ; i < n; ++i) {
100- c = 0 ;
101- DO (m , t = u [i ]; if (c = 0 > t ? iv [i ] < t + s [i ] : iv [i ] >= t ) break ;);
102- if (!c ) {
106+
107+ // this is std::mismatch3 (or std::zip_find3)
108+ bool cc = 0 ;
109+ for (int64_t i = 0 ; i < m; ++i) {
110+ t = u[i];
111+ if (0 > t ? iv[i] < t + s[i] : iv[i] >= t) {
112+ cc = true ;
113+ break ;
114+ }
115+ }
116+
117+ if (!cc) {
103118 ++d;
104119 memcpy (yv, xv, k);
105120 yv += k;
121+ // TODO: use algorithm created above
106122 DO (m, t = u[i]; *jv++ = 0 > t ? iv[i] - (t + s[i]) : iv[i];);
107123 }
108124 iv += m;
@@ -197,7 +213,7 @@ jttake(J jt, A a, A w) {
197213 wf = wr - wcr;
198214 RESETRANK;
199215 if (((af - 1 ) & (acr - 2 )) >= 0 ) {
200- s = rank2ex (a , w , UNUSED_VALUE , MIN (acr , 1 ), wcr , acr , wcr , jttake ); // if multiple x values, loop over them
216+ s = rank2ex (a, w, UNUSED_VALUE, MIN (acr, 1 ), wcr, acr, wcr, reinterpret_cast <AF>( jttake) ); // if multiple x values, loop over them
201217 // af>0 or acr>1
202218 // We extracted from w, so mark it (or its backer if virtual) non-pristine. There may be replication (if there
203219 // was fill), so we don't pass pristinity through We overwrite w because it is no longer in use
@@ -212,7 +228,7 @@ jttake(J jt, A a, A w) {
212228 jtvib (jt, a)); // convert input to integer, auditing for illegal values; and convert infinities to IMAX/-IMAX
213229 // if the input was not INT/bool, we go through and replace any infinities with the length of the axis. If we do
214230 // this, we have to clone the area, because vib might return a canned value
215- if (!(AT (a ) & B01 + INT )) {
231+ if (!(AT (a) & ( B01 + INT) )) {
216232 I i;
217233 for (i = 0 ; i < AN (s); ++i) {
218234 I m = IAV (s)[i];
@@ -298,7 +314,7 @@ jtdrop(J jt, A a, A w) {
298314 // special case: if a is atomic 0, and cells of w are not atomic
299315 if ((-wcr & (ar - 1 )) < 0 && (IAV (a)[0 ] == 0 )) return w; // 0 }. y, return y
300316 if (((af - 1 ) & (acr - 2 )) >= 0 ) {
301- s = rank2ex (a , w , UNUSED_VALUE , MIN (acr , 1 ), wcr , acr , wcr , jtdrop ); // if multiple x values, loop over them
317+ s = rank2ex (a, w, UNUSED_VALUE, MIN (acr, 1 ), wcr, acr, wcr, reinterpret_cast <AF>( jtdrop) ); // if multiple x values, loop over them
302318 // af>0 or acr>1
303319 // We extracted from w, so mark it (or its backer if virtual) non-pristine. There may be replication, so we
304320 // don't pass pristinity through We overwrite w because it is no longer in use
@@ -411,7 +427,7 @@ jthead(J jt, A w) {
411427 return jtfrom (jtinplace, zeroionei (0 ), w); // could call jtfromi directly for non-sparse w
412428 }
413429 } else {
414- return SPARSE & AT (w ) ? irs2 (num (0 ), jttake (jt , num (1 ), w ), 0L , 0L , wcr , jtfrom )
430+ return SPARSE & AT (w) ? irs2 (num (0 ), jttake (jt, num (1 ), w), 0L , 0L , wcr, reinterpret_cast <AF>( jtfrom) )
415431 : jtrsh0 (jt, w); // cell of w is empty - create a cell of fills jt->ranks is still set
416432 // for use in take. Left rank is garbage, but that's OK
417433 }
@@ -429,7 +445,7 @@ jttail(J jt, A w) {
429445 return !wcr || AS (w)[wf] ? jtfrom (jtinplace, num (-1 ), w)
430446 : // if cells are atoms, or if the cells are nonempty arrays, result is last cell(s) scaf
431447 // should generate virtual block here for speed
432- SPARSE & AT (w ) ? irs2 (num (0 ), jttake (jt , num (-1 ), w ), 0L , 0L , wcr , jtfrom )
448+ SPARSE & AT (w) ? irs2 (num (0 ), jttake (jt, num (-1 ), w), 0L , 0L , wcr, reinterpret_cast <AF>( jtfrom) )
433449 : jtrsh0 (jt, w);
434450 // pristinity from other verbs
435451}
0 commit comments