4

Assuming I have an array N ← 0 0 0 1 1 1 0 0 1, how can I apply the scan \ to achieve the array 0 0 0 1 2 3 0 0 1?

+\N gives me 0 0 0 1 2 3 3 3 4 which is not what I want.

+\¨⊆⍨N gives me | 1 2 3 | 1 | which is closer, but then I lose the positions.

Is there a way to carry the original values in the scan and multiply, or perhaps a better way?

mazin
  • 395
  • 2
  • 7

2 Answers2

5

How about m←{s-⌈\(s←+\⍵)×2>/0,⍵}, seems about twice as fast?

      cmpx  'h r' 'm r'
  h r → 1.1E¯5 |   0% ⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕
  m r → 4.2E¯6 | -63% ⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕ 
Morten Kromberg
  • 643
  • 5
  • 5
4

There are a couple of options here. Your original idea can be adapted easily using \.

Alternatively, for a short (but inefficient O(n^2)) solution, ⊥⍨¨,\ works.

For a more efficient but longer solution, I adapted https://aplcart.info/?q=cumulative%20sum#

There's probably something even better but I'm too bad to find it but it's left as an exercise to the reader ;)

      f ← {⍵\∊+\¨⊆⍨⍵}
      g ← ⊥⍨¨,\
      h ← {+\⍵-a\¯2-/0,(a←1,2≠/⍵)/+\¯1↓0,⍵}
      f 0 0 0 1 1 1 0 0 1
0 0 0 1 2 3 0 0 1

      r ← ? 1e3 ⍴ 2        ⍝ random boolean array
      (∧/2≡/f,⍥⊆g,⍥⊆h)r   ⍝ they're all the same
1
      
      ]runtime -c 'f r' 'g r' 'h r'
                                                                
  f r → 3.6E¯5 |    0% ⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕                      
  g r → 7.7E¯5 | +111% ⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕⎕ 
  h r → 7.3E¯6 |  -80% ⎕⎕⎕⎕                                     
rak1507
  • 392
  • 3
  • 6
  • Could you elaborate on the first paragraph please. – mazin Sep 17 '21 at 09:10
  • Dyadic \ is expand https://help.dyalog.com/18.0/Content/Language/Primitive%20Functions/Expand.htm which does exactly what you want – rak1507 Sep 17 '21 at 09:11
  • But it doesn't. You say it can be adapted, but you do not say how! – mazin Sep 17 '21 at 09:14
  • 0 0 0 1 1 1 0 0 1 \ 1 2 3 1 is 0 0 0 1 2 3 0 0 1, which puts the items back in the right place – rak1507 Sep 17 '21 at 09:15
  • Ah. Ok. I didn't think of that! Now it makes sense. Thanks – mazin Sep 17 '21 at 09:17
  • 2
    Btw, the chatroom https://chat.stackexchange.com/rooms/52405/the-apl-orchard/ (or apl.chat) is also useful for asking questions if you don't know about it :) – rak1507 Sep 17 '21 at 09:21
  • Nope, give me a LENGTH ERROR! – mazin Sep 17 '21 at 09:21
  • 1
    You need to flatten the array with ∊ first – rak1507 Sep 17 '21 at 09:22
  • 1
    Your adaptation of `{+⍀⍵-⍺⍀¯2-⌿0⍪⍺⌿+⍀¯1↓0⍪⍵}` to `{+\⍵-a\¯2-/0,(a←1,2≠/⍵)/+\¯1↓0,⍵}` is overly complicated for `{+⍀⍵-n⍀¯2-⌿0⍪(n←~⍵)⌿+⍀¯1↓0⍪⍵}` will do. – Adám Sep 17 '21 at 09:56