« first day (441 days earlier)      last day (2223 days later) » 
06:00 - 23:0023:00 - 00:00

6:25 AM
Adám has added an event to this room's schedule.
 
 
1 hour later…
ngn
7:29 AM
@Adám I voted yes, though I think such regular sessions would still be useful even if they don't take the form of lessons.
 
 
2 hours later…
9:36 AM
@Adám Having some sessions as challenge practice would be quite useful, IMO. That's how I learnt Jelly, by doing a bunch of CMCs to find the shortest solution.
 
@cairdcoinheringaahing OK, but then we have to come up with some nice problems.
 
@Adám shouldn't be too hard; saying this after having made a list of easy-to-medium challenges myself, and also who is "we"?
 
@EriktheOutgolfer Anyone willing.
 
 
4 hours later…
1:20 PM
I'm not the best challenge maker but I sure can try to solve some :p
 
challenge suggestion: implement a ⍋-like operator which maps a custom function for grading
you can use ⍋ inside it
the function should apply to the minor cells
 
@EriktheOutgolfer Interesting idea. We did a lot of that when working on TAO. What should the operand be? A boolean like or a cmp like >-<?
@EriktheOutgolfer Minor‽ Not major?
 
@Adám well, of course it's not final yet :P
on one hand, ¨ applies to minor cells, on the other hand, ⍋ is applied to major cells
 
@EriktheOutgolfer Which is why you have to tell APL exactly what you want.
 
@Adám yeah I thought about that
but there's still a dilemma
 
1:29 PM
@EriktheOutgolfer Interested in something I wrote about sorting in APL? It is only available on Dyalog's internal wiki (i.e. not viewable by the public).
@EriktheOutgolfer Which dilemma?
 
@Adám respect ⍋ or respect ¨?
hm, I'd say the latter can be changed to ⍤
 
@EriktheOutgolfer Obviously since you're writing an alternative to .
 
@Adám I think so, since the idea is that ⍋ applies ⍺⍺ to each piece of ⍵ it evaluates
 
@EriktheOutgolfer I think for simplicity, the challenge should just be to be able to grade a vector. Anything more is just a matter of recursion and/or rank.
 
@Adám then the solution is 1 byte...
 
1:35 PM
@EriktheOutgolfer Wat?
 
Ven
Is the order for ⌸ and ∪ reliable?
 
@Ven Yes.
 
@Adám "just to be able to grade a vector" is exactly , no?
 
@EriktheOutgolfer No, you were asking for an operator which takes a comparison function as operand and grades using that.
 
@Adám oh you mean be able to grade the vector with a function
 
1:37 PM
Let's call that operator $. Then ≤$ would be the equivalent of and ≥$ would be (for simple numeric vectors).
@EriktheOutgolfer Yeah, isn't that what you meant? Otherwise the solution is just (17.0's) .
 
Ven
Now that's a tease. Are there slides about 17.0?
 
Then we could have another operator which takes a simple comparison function as operand and derives the corresponding precedence function. If we call that operator % then ≤% would be the equivalent of math's ≼. And so ⍋%$ would be the equivalent of 17.0's .
 
Ven
⎕←$
 
@Ven
SYNTAX ERROR
 
Ven
Ah. Whoops.
 
1:41 PM
@Adám ah no, that's not what I meant
 
@Ven I gave a webinar about it.
 
no, the function isn't a "comparison function"
 
Ven
@Adám Alright, I need to go check it out. I remember watching your webinar about the fall challenge, but not this.
 
it's just applied to every major cell and then the comparison happens
 
@EriktheOutgolfer Ah, you mean it is like a preprocessor to ?
 
1:44 PM
@Adám I think so
@Adám lol what's with the Chinese there
 
Ven
@Adám What do the chinese characters at the beginning mean?
the first 2 looks like "ki"
 
@Ven wait, you know Chinese?
 
@EriktheOutgolfer Isn't the solution just {⍋ ⍺⍺⍤¯1⊢⍵}
 
Ven
@EriktheOutgolfer no, but I know a bit of japanese
 
@Adám yeah it's kind of easy tbf
but I thought it's actually {⍋⍺⍺⍤1⊢⍵}, since major cells are 1, not ¯1, no?
 
1:47 PM
@EriktheOutgolfer @Ven 大道至簡 means The greatest TAO is the simplest one.
@EriktheOutgolfer Right, but ⍤1 means apply to arrays of rank 1 while ⍤¯1 means apply to arrays of rank one less than the rank of the argument.
 
@Adám I assume TAO here doesn't mean Total Array Ordering? :p
 
Ven
I guess that's the joke :D.
 
@J.Sallé No, it means a way (of life) but that still applies to TAO.
 
Programmers' jokes are never simple
 
TAO: A simple way of life
 
Ven
1:49 PM
So 道 is Tao/TAO. Got it.
 
Also, the symbol for Tao is ☯ which lead me to design the APL TAO symbol, and have it made into biscuits which I handed out to my colleagues in celebration of our team work that made TAO a reality:
Adam surprises us with biscuits as a celebration of all sorts of things coming in version 17.
 
Ven
That's amazing
 
And delicious, I'd wager.
 
Ven
2:31 PM
Ok, the parse of 10 20@2 4 ⍳5 surprised me... I thought this was going to be parsed as 10 20@(2 4⍳5)
 
@Ven @ is an operator, so it binds stronger than the function.
 
Ven
@Adám I see. I have a question: can the @ operator take a "all for this dimension"? let's say I want to change all the 2nd values of a nested matrix
⎕←100@(⊂0 2)4 4⍴⍳16
 
@Ven
RANK ERROR
 
@Ven I don't understand. ⍳16 isn't nested.
 
Ven
⎕←a←4 4⍴⍳16⋄a[2 ;]←100⋄a
 
2:38 PM
@Ven
 1  2  3  4
 5  6  7  8
 9 10 11 12
13 14 15 16
 
Ven
augh. obviously...
⎕←{v←⍵⋄v[2 ;]←100⋄v}4 4⍴⍳16
 
@Ven
  1   2   3   4
100 100 100 100
  9  10  11  12
 13  14  15  16
 
Ven
This is what I meant...
 
⎕←100@2⊢4 4⍴⍳16
 
@Adám
  1   2   3   4
100 100 100 100
  9  10  11  12
 13  14  15  16
 
Ven
2:40 PM
⎕←{v←⍵⋄v[; 2]←100⋄v}4 4⍴⍳16
 
@Ven
 1 100  3  4
 5 100  7  8
 9 100 11 12
13 100 15 16
 
Ven
and for this version?
 
⎕←100@2⍤1⊢4 4⍴⍳16
 
@Adám
 1 100  3  4
 5 100  7  8
 9 100 11 12
13 100 15 16
 
⎕←⍉100@2⍉4 4⍴⍳16
@DyalogAPL Hello?
⎕←⍉100@2⍉4 4⍴⍳16
)about
 
2:42 PM
@Adám You can evaluate an APL expression by typing it into chat prefixed by ⍞←. Use ⎕← instead for boxed display and multi-line results. Do not use markdown. Commands: )lb for language bar, )help for table of language elements, )docs for full documentation, )ref for PDF reference card, )idioms for idiom list.
 
@DyalogAPL Can I really?
⎕←⍉100@2⍉4 4⍴⍳16
 
@Adám
 1 100  3  4
 5 100  7  8
 9 100 11 12
13 100 15 16
 
@DyalogAPL Thank you!
 
Dyalog bot just needed a little rest
 
Lazy boy! Let's put him to work:
⍞←⎕DL 55
@Ven Did these answer your question?
 
Ven
2:45 PM
@Adám Yes, thank you! I'm still struggling, but (I think) for a different reason now :-).
 
@Adám 55.05507
 
Ven
⎕←{1000⋄⍵}10
 
@Ven
1000
 
Ven
Aaah... I must return the same number of elements
⎕←⍴@2⍤1⊢↑{⊂⍺⍵}⌸'Mississippi'
 
@Ven
LENGTH ERROR
 
Ven
2:48 PM
I was trying to do that, but it doesn't work, because it goes from N values to 1, I suppose...
 
⎕←(⊣,' '∘,)/200⍴⊂'I will never crash again!'
 
@EriktheOutgolfer
SYNTAX ERROR
 
@Ven ↑{⊂⍺⍵}⌸'Mississippi' is the same as {⍺⍵}⌸'Mississippi'
 
⎕←(⊣,' ',⊢)/200⍴⊂'I will never crash again!'
 
@EriktheOutgolfer
┌──────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────
 
Ven
2:49 PM
@Adám Oh, yeah. Duh.
 
@Ven Uh:
⎕←⍴¨@2⍤1{⍺⍵}⌸'Mississippi'
 
@Adám
┌─┬─┐
│M│1│
├─┼─┤
│i│4│
├─┼─┤
│s│4│
├─┼─┤
│p│2│
└─┴─┘
 
But why not just:
⎕←{⍺(≢⍵)}⌸'Mississippi'
 
@Adám
M 1
i 4
s 4
p 2
 
Ven
@Adám Just toying around with these :).
 
2:51 PM
@Ven OK. Btw, shorter:
⎕←,∘≢⌸'Mississippi'
 
@Adám
M 1
i 4
s 4
p 2
 
Ven
@ is so powerful, I was trying to see how many things I could do. The answer is: more than I wanted/needed.
⎕←{⍺('ABCDEFGHIJK'[⍵])}⌸'Mississippi'
 
@Ven
┌─┬────┐
│M│A   │
├─┼────┤
│i│BEHK│
├─┼────┤
│s│CDFG│
├─┼────┤
│p│IJ  │
└─┴────┘
 
@Ven In fact it can do 6 things:
⎕←⍕'  A' '  f' 'X f'∘.{⍺,'@',⍵,' Y '}'g' 'B ⊢'
 
@Adám
  A@g Y     A@B ⊢ Y
  f@g Y     f@B ⊢ Y
 X f@g Y   X f@B ⊢ Y
 
2:59 PM
Hm, it looks like the bot is dropping spaces…
 
Ven
When I started going through the Mastering Dyalog APL book, this was the one thing I wanted the most, I think.
A way to remove mutations, not force me to store ⍵ to modify it, and concise while readable.
 
⎕←'   three' ⋄ ⎕←'  two' ⋄ ⎕←' one' ⋄ ⎕←'zero'
 
@Adám
 three
 two
 one
zero
 
@Ven Yeah, it was the last (?) piece missing to allow APL to be completely functional (as in functional programming).
 
Ven
Right, this is exactly how it looks like from my newbie PoV as well.
 
3:02 PM
@Ven Actually, there's one more thing missing…
⎕←A←2 2⍴(1 2 3)(4 5)6(7(8 9)) ⋄ UnderEnlist←{⍺←⊢ ⋄ w←⍵ ⋄ (∊w)←⍺ ⍺⍺ ∊⍵ ⋄ w} ⋄ ⎕←⌽UnderEnlist A
 
@Adám
┌─────┬───────┐
│1 2 3│4 5    │
├─────┼───────┤
│6    │┌─┬───┐│
│     ││7│8 9││
│     │└─┴───┘│
└─────┴───────┘
┌─────┬───────┐
│9 8 7│6 5    │
├─────┼───────┤
│4    │┌─┬───┐│
│     ││3│2 1││
│     │└─┴───┘│
└─────┴───────┘
 
1 message moved to trash
1 message moved to trash
 
Ven
@Adám ⍺←⊢? Is that just to force the parse to be someway?
 
@Ven No, what it does is to make the identity function if and only if a left argument was not supplied. This way the subsequent code becomes ambiguous: ⍺ ⍺⍺ ∊⍵ is just ⍺⍺ ∊⍵ if no left argument was given, but A ⍺⍺ ∊⍵ if the left argument was A.
 
Ven
Oh, you assign it to tack. Duh.
That's a beautiful trick.
 
3:12 PM
@Ven Yeah, this is a neat way to make your functions ambivalent. E.g. a cover function for minus could be {⍺←⊢ ⋄ ⍺-⍵} or {⍺←0 ⋄ ⍺-⍵}.
 
@Ven been there, done that
 
Ooh, I found two neat solutions to:
100
Q: I'm a palindrome. Are you?

user62131 There have been a couple of previous attempts to ask this question, but neither conforms to modern standards on this site. Per discussion on Meta, I'm reposting it in a way that allows for fair competition under our modern rulesets. Background A palindrome is a string that "reads the same f...

 
3:35 PM
@Feeds Can you figure it out?
Actually, I've found three.
 
I'll try that one
 
4:26 PM
#onelinerwednesday How about a palindromic function to check if its argument is palindromic? ⌽≡⊢⊢≡⌽ Try it here: http://tryapl.org/?a=%28%u233D%u2261%u22A2%u22A2%u2261%u233D%29%27%u233D%u2261%u22A2%u22A2%u2261%u233D%27&run
And for extra fun, how about a symmetrical version of the function? ⌷≡⌽⌽≡⌷ http://tryapl.org/?a=%28%u2337%u2261%u233D%u233D%u2261%u2337%29%27%u2337%u2261%u233D%u233D%u2261%u2337%27&run #starwars #onelinerwednesday
 
 
1 hour later…
5:30 PM
Welcome to the APL Cultivation!
 
2 and a half m...inutes
 
This week, we'll speak about function application, and how to get a better grip of that.
@EriktheOutgolfer What?
 
@Adám like, that many minutes earlier than 18:30+0, and also looks like you didn't get the pun
 
Next week, we can conveniently speak about multithreading using APL threads, as there is a webinar the day after on multithreading using OS threads.
@EriktheOutgolfer It sure wasn't early according to my computer clock.
 
@Adám mine is earlier than many other clocks tbf...
 
5:33 PM
So, some operators apply (to) their operands in intricate ways. How do you get a clearer picture of what they actually do?
Let's take outer product ∘.f as an example.
⎕←10 20 30∘.×1 2 3 4
 
@Adám
10 20 30  40
20 40 60  80
30 60 90 120
 
Sure, ok, but what actually happened?
It may seem simple, bu what about:
⎕←(3 2⍴10×⍳6)∘.×(2 4⍴⍳8)
 
@Adám
 10  20  30  40
 50  60  70  80

 20  40  60  80
100 120 140 160


 30  60  90 120
150 180 210 240

 40  80 120 160
200 240 280 320


 50 100 150 200
250 300 350 400

 60 120 180 240
300 360 420 480
 
What exactly got paired up with what?
Here's a trick you can use to analyse derived functions, that is both functions modified by operators and all tacit functions in general.
Let's replace the function (the operand) with a function which doesn't actually do the computation, but rather tells us what the computation would be:
⍞←10 20 30{'(',⍺,'×',⍵,')'}1 2 3
 
@Adám ( 10 20 30 × 1 2 3 )
 
5:41 PM
× is scalar. We can model that too:
⍞←10 20 30{⍺{'(',⍺,'×',⍵,')'}¨⍵}1 2 3
 
@Adám  ( 10 × 1 )  ( 20 × 2 )  ( 30 × 3 )
 
⎕←(3 2⍴10×⍳6)∘.{⍺{'(',⍺,'×',⍵,')'}¨⍵}(2 4⍴⍳8)
 
@Adám
┌────────────┬────────────┬────────────┬────────────┐
│┌──────────┐│┌──────────┐│┌──────────┐│┌──────────┐│
││( 10 × 1 )│││( 10 × 2 )│││( 10 × 3 )│││( 10 × 4 )││
│└──────────┘│└──────────┘│└──────────┘│└──────────┘│
├────────────┼────────────┼────────────┼────────────┤
│┌──────────┐│┌──────────┐│┌──────────┐│┌──────────┐│
││( 10 × 5 )│││( 10 × 6 )│││( 10 × 7 )│││( 10 × 8 )││
│└──────────┘│└──────────┘│└──────────┘│└──────────┘│
└────────────┴────────────┴────────────┴────────────┘
┌────────────┬────────────┬────────────┬────────────┐
 
Now we can see what's going on!
Even better if we use indices as arguments:
 
@Adám yup, I had that kinda figured out from seeing it before
that's a cool trick to show what's happening, btw
 
5:47 PM
⎕←({⊂'⍺[',(⍕1⊃⍵),';',(⍕2⊃⍵),']'}¨⍳2 3)∘.{⍺{'(',⍺,'×',⍵,')'}¨⍵}({⊂'⍺[',(⍕1⊃⍵),';',(⍕2⊃⍵),']'}¨⍳2 4)
 
@Adám
┌─────────────────┬─────────────────┬─────────────────┬─────────────────┐
│┌───────────────┐│┌───────────────┐│┌───────────────┐│┌───────────────┐│
││(⍺[1;1]×⍺[1;1])│││(⍺[1;1]×⍺[1;2])│││(⍺[1;1]×⍺[1;3])│││(⍺[1;1]×⍺[1;4])││
│└───────────────┘│└───────────────┘│└───────────────┘│└───────────────┘│
├─────────────────┼─────────────────┼─────────────────┼─────────────────┤
│┌───────────────┐│┌───────────────┐│┌───────────────┐│┌───────────────┐│
││(⍺[1;1]×⍺[2;1])│││(⍺[1;1]×⍺[2;2])│││(⍺[1;1]×⍺[2;3])│││(⍺[1;1]×⍺[2;4])││
 
Oops, that right-side should have been an , but you get the idea.
We can make an "eXplanation" operator: X←{f←⍺⍺ ⋄ ⍺←⊢ ⋄ '(',⍺,(⎕CR'f'),⍵,')'}
How does it work?
First it captures its operand ⍺⍺ as f, then it makes into identity which is a common trick to make ambivalent functions. Finally, it strings together the left arg, the function character representation, and the right arg.
⎕←X←{f←⍺⍺ ⋄ ⍺←⊢ ⋄ '(',⍺,(⎕CR'f'),⍵,')'} ⋄ ⎕←'abc'∘.(×X)'DEF'
 
@Adám
{f←⍺⍺ ⋄ ⍺←⊢ ⋄ '(',⍺,(⎕CR'f'),⍵,')'}
┌─────┬─────┬─────┐
│(a×D)│(a×E)│(a×F)│
├─────┼─────┼─────┤
│(b×D)│(b×E)│(b×F)│
├─────┼─────┼─────┤
│(c×D)│(c×E)│(c×F)│
└─────┴─────┴─────┘
 
OK, now that we have a grip on ∘.f, let's look at f.g.
⎕←X←{f←⍺⍺ ⋄ ⍺←⊢ ⋄ '(',⍺,(⎕CR'f'),⍵,')'} ⋄ ⎕←'abc'(+X).(×X)'DEF'
 
@Adám
{f←⍺⍺ ⋄ ⍺←⊢ ⋄ '(',⍺,(⎕CR'f'),⍵,')'}
┌─────────────────────┐
│((a×D)+((b×E)+(c×F)))│
└─────────────────────┘
 
5:53 PM
The result is enclosed which shows us that if the arguments are vectors (as in this case) then the result is a scalar.
What happens with higher-rank arguments?
 
Something cool, I assume :p
 
⎕←X←{f←⍺⍺ ⋄ ⍺←⊢ ⋄ '(',⍺,(⎕CR'f'),⍵,')'} ⋄ ⎕←'abc'(+X).(×X)(3 2⍴'DEFGHI')
 
@Adám
{f←⍺⍺ ⋄ ⍺←⊢ ⋄ '(',⍺,(⎕CR'f'),⍵,')'}
┌─────────────────────┬─────────────────────┐
│((a×D)+((b×F)+(c×H)))│((a×E)+((b×G)+(c×I)))│
└─────────────────────┴─────────────────────┘
 
The left argument was a 3-element vector and the right argument a 3-by-2 matrix.
We can see how the left argument cells were distributed to the right argument cells.
⎕←X←{f←⍺⍺ ⋄ ⍺←⊢ ⋄ '(',⍺,(⎕CR'f'),⍵,')'} ⋄ ⎕←(2 3⍴'abcdef')(+X).(×X)3 2⍴'DEFGHI'
 
@Adám
{f←⍺⍺ ⋄ ⍺←⊢ ⋄ '(',⍺,(⎕CR'f'),⍵,')'}
┌─────────────────────┬─────────────────────┐
│((a×D)+((b×F)+(c×H)))│((a×E)+((b×G)+(c×I)))│
├─────────────────────┼─────────────────────┤
│((d×D)+((e×F)+(f×H)))│((d×E)+((e×G)+(f×I)))│
└─────────────────────┴─────────────────────┘
 
5:56 PM
OK, now it is getting more interesting. The left arg was 2 3⍴ and the right was 3 2⍴.
The result became 2 2⍴.
In fact, the rule is that f.g removes the last axis of the left argument and the first axis of the right argument, so the result has the shape (¯1↓⍴⍺),(1↓⍴⍵).
 
well it makes sense when you look at it, but I couldn't tell it just by seeing the function work
 
@J.Sallé So does this illustration help clarify?
 
@DyalogAPL this one certainly does.
 
@DyalogAPL :O matrix multiplication
 
So if the left arg is shape 2 4 3 and the right arg is 3 5 1 the result should be shape 2 4 5 1:
 
6:00 PM
@Cowsquack no, dot product
 
⍞←⍴(2 4 3⍴0)+.×(3 5 1⍴0)
 
@Adám 2 4 5 1
 
(+.× is pretty standard)
 
@EriktheOutgolfer No, both.
Now let's go back to ∘.f for a moment. What is the rule about the shape of the result of that?
 
@Adám ah, never did I picture them as related like that before
 
6:01 PM
@EriktheOutgolfer APL opens the mind.
 
yeah on vectors it's dot product and on matrices it's matrix multiplication
 
The people who designed APL were very clever, and saw parallels nobody else saw.
⍞←⍴(2 4 3⍴0)∘.×(3 5 1⍴0)
 
@Adám 2 4 3 3 5 1
 
So the shape of ∘.f is (⍴⍺),(⍴⍵). ∘.f and f.g are definitely related!
 
The plot thickens
 
6:06 PM
In fact, Iverson suggested that the slightly anomalous in ∘.f be replaced with a number that indicates how many axes to combine. This way 0.f would be ∘.f. However, there is a more general alternative.
.
The powerful operator that few seem to get a proper grasp of. Let's explore it!
 
@Adám because it's a syntax error, no?
 
@EriktheOutgolfer No, it happens to be a syntax error on its own, but I meant that few know how to use it properly.
 
@Adám I certainly don't. I don't think I've ever even used that without raising errors >.>
 
I'll use a slightly modified X now.
⎕←X←{f←⍺⍺ ⋄ ⍺←'' ⋄ '(',(⍕⍺(⎕CR'f')⍵),')'} ⋄ (⊂X)2 3 4⍴⎕A
 
@Adám
{f←⍺⍺ ⋄ ⍺←'' ⋄ '(',(⍕⍺(⎕CR'f')⍵),')'}
 
6:14 PM
⎕←X←{f←⍺⍺ ⋄ ⍺←'' ⋄ '(',(⍕⍺(⎕CR'f')⍵),')'} ⋄ ⎕←(⊂X)2 3 4⍴⎕A
 
@Adám
{f←⍺⍺ ⋄ ⍺←'' ⋄ '(',(⍕⍺(⎕CR'f')⍵),')'}
(   ⊂  ABCD )
(      EFGH )
(      IJKL )
(           )
(      MNOP )
(      QRST )
(      UVWX )
 
OK, this just shows enclosing the rank-3 alphabet.
⎕←X←{f←⍺⍺ ⋄ ⍺←'' ⋄ '(',(⍕⍺(⎕CR'f')⍵),')'} ⋄ ⎕←(⊂X)⍤¯1⊢2 3 4⍴⎕A
 
@Adám
{f←⍺⍺ ⋄ ⍺←'' ⋄ '(',(⍕⍺(⎕CR'f')⍵),')'}
(   ⊂  ABCD )
(      EFGH )
(      IJKL )

(   ⊂  MNOP )
(      QRST )
(      UVWX )
 
Let's begin with negative rank, which is often what you really want.
f⍤¯N ⊢ B applies the function to cells of rank (≢⍴B)-N.
So in this case the array had rank 3, and the function was applied to sub-arrays of rank 3-1, that is 2, i.e. matrices.
⎕←X←{f←⍺⍺ ⋄ ⍺←'' ⋄ '(',(⍕⍺(⎕CR'f')⍵),')'} ⋄ ⎕←(⊂X)⍤¯2⊢2 3 4⍴⎕A
 
@Adám
{f←⍺⍺ ⋄ ⍺←'' ⋄ '(',(⍕⍺(⎕CR'f')⍵),')'}
(   ⊂  ABCD )
(   ⊂  EFGH )
(   ⊂  IJKL )

(   ⊂  MNOP )
(   ⊂  QRST )
(   ⊂  UVWX )
 
6:18 PM
And here, the function was applied to sub-arrays of rank 3-2, that is 1, i.e. vectors.
Still following? Now lets try positive rank.
⎕←X←{f←⍺⍺ ⋄ ⍺←'' ⋄ '(',(⍕⍺(⎕CR'f')⍵),')'} ⋄ ⎕←(⊂X)⍤1⊢2 3 4⍴⎕A
 
@Adám
{f←⍺⍺ ⋄ ⍺←'' ⋄ '(',(⍕⍺(⎕CR'f')⍵),')'}
(   ⊂  ABCD )
(   ⊂  EFGH )
(   ⊂  IJKL )

(   ⊂  MNOP )
(   ⊂  QRST )
(   ⊂  UVWX )
 
f⍤N apples the function to sub-arrays of rank N. So f⍤1 digs in until it finds vectors.
⎕←X←{f←⍺⍺ ⋄ ⍺←'' ⋄ '(',(⍕⍺(⎕CR'f')⍵),')'} ⋄ ⎕←(⊂X)⍤2⊢2 3 4⍴⎕A
 
@Adám
{f←⍺⍺ ⋄ ⍺←'' ⋄ '(',(⍕⍺(⎕CR'f')⍵),')'}
(   ⊂  ABCD )
(      EFGH )
(      IJKL )

(   ⊂  MNOP )
(      QRST )
(      UVWX )
 
So too does ⍤2 apply the function to matrices.
What about ⍤0?
 
@Adám apply to every rank?
 
6:25 PM
It applies the function to sub-arrays of rank 0, i.e. scalars. obviously isn't a useful function on scalars, but some functions are, e.g.
Consider e.g. the nested array:
⎕←2 2⍴(2 3⍴⎕A)(3 2⍴⎕A)(2 2⍴⎕A)(3 3⍴⎕A)
 
@Adám
┌───┬───┐
│ABC│AB │
│DEF│CD │
│   │EF │
├───┼───┤
│AB │ABC│
│CD │DEF│
│   │GHI│
└───┴───┘
 
It has four scalars. We can apply on each scalar:
⎕←∊⍤0⊢2 2⍴(2 3⍴⎕A)(3 2⍴⎕A)(2 2⍴⎕A)(3 3⍴⎕A)
 
@Adám
ABCDEF
ABCDEF

ABCD
ABCDEFGHI
 
Ah, but notice the description: on each. In general, ⍤0 is the same as ¨:
⎕←∊¨2 2⍴(2 3⍴⎕A)(3 2⍴⎕A)(2 2⍴⎕A)(3 3⍴⎕A)
 
@Adám
┌──────┬─────────┐
│ABCDEF│ABCDEF   │
├──────┼─────────┤
│ABCD  │ABCDEFGHI│
└──────┴─────────┘
 
6:28 PM
Except "mixes" the results while ¨ encloses them.
⎕←↑∊¨2 2⍴(2 3⍴⎕A)(3 2⍴⎕A)(2 2⍴⎕A)(3 3⍴⎕A)
 
@Adám
ABCDEF
ABCDEF

ABCD
ABCDEFGHI
 
⎕←⊂∘∊⍤0⊢2 2⍴(2 3⍴⎕A)(3 2⍴⎕A)(2 2⍴⎕A)(3 3⍴⎕A)
 
@Adám
┌──────┬─────────┐
│ABCDEF│ABCDEF   │
├──────┼─────────┤
│ABCD  │ABCDEFGHI│
└──────┴─────────┘
 
Actually, rank can do more than just that, in a powerful way that ¨ cannot compare to.
The derived function can be applied dyadically.
 
@Adám heh, the absolute humiliation of ¨
 
6:31 PM
⎕←X←{f←⍺⍺ ⋄ ⍺←'' ⋄ '(',(⍕⍺(⎕CR'f')⍵),')'} ⋄ ⎕←(819⌶2 3 4⍴⎕A)(,X)⍤1⊢2 3 4⍴⎕A
 
@Adám
{f←⍺⍺ ⋄ ⍺←'' ⋄ '(',(⍕⍺(⎕CR'f')⍵),')'}
( abcd  ,  ABCD )
( efgh  ,  EFGH )
( ijkl  ,  IJKL )

( mnop  ,  MNOP )
( qrst  ,  QRST )
( uvwx  ,  UVWX )
 
I'm concatenating the rank-1 sub-arrays of the arguments.
Let's use different ranks for the left and right arguments!
 
@Adám oooh shiz that's nice
 
Left arg will be:
⎕←819⌶2 2⍴⎕A
 
@Adám
ab
cd
 
6:34 PM
And right arg:
⎕←2 2 2⍴⎕A
 
@Adám
AB
CD

EF
GH
 
⎕←X←{f←⍺⍺ ⋄ ⍺←'' ⋄ '(',(⍕⍺(⎕CR'f')⍵),')'} ⋄ ⎕←(819⌶2 2⍴⎕A)(,X)⍤1 2⊢2 2 2⍴⎕A
 
@Adám
{f←⍺⍺ ⋄ ⍺←'' ⋄ '(',(⍕⍺(⎕CR'f')⍵),')'}
( ab  ,  AB )
(        CD )

( cd  ,  EF )
(        GH )
 
So here, we are concatenating rank-1 sub-arrays of the left arg with rank-2 sub-arrays of the right arg:
⎕←(819⌶2 2⍴⎕A),⍤1 2⊢2 2 2⍴⎕A
 
@Adám
aAB
bCD

cEF
dGH
 
6:37 PM
Quiz: Now can anyone figure out what Y is so that f⍤Y is ∘.f?
Remember:
⎕←X←{f←⍺⍺ ⋄ ⍺←'' ⋄ '(',(⍕⍺(⎕CR'f')⍵),')'} ⋄ ⎕←(819⌶2 2⍴⎕A)∘.(,X)3 2⍴⎕A
 
@Adám
{f←⍺⍺ ⋄ ⍺←'' ⋄ '(',(⍕⍺(⎕CR'f')⍵),')'}
┌───────┬───────┐
│(a , A)│(a , B)│
├───────┼───────┤
│(a , C)│(a , D)│
├───────┼───────┤
│(a , E)│(a , F)│
└───────┴───────┘
┌───────┬───────┐
│(b , A)│(b , B)│
├───────┼───────┤
│(b , C)│(b , D)│
├───────┼───────┤
│(b , E)│(b , F)│
└───────┴───────┘

┌───────┬───────┐
│(c , A)│(c , B)│
├───────┼───────┤
│(c , C)│(c , D)│
├───────┼───────┤
│(c , E)│(c , F)│
└───────┴───────┘
┌───────┬───────┐
│(d , A)│(d , B)│
├───────┼───────┤
│(d , C)│(d , D)│
├───────┼───────┤
 
So notice that each scalar in got paired up with the entire .
 
@Adám 0 15?
 
@H.PWiz Yes, very nice!
In other words, we need the left rank to be 0 and the right rank to be infinite. But since Dyalog APL only allows arrays of up to rank 15, that is enough. (15 = ∞ for very small values of ∞.)
⍤N can also take a three-element N. That's only useful for ambivalent functions. It then means that if the derived function is applied monadically, it gets applied to sub-arrays of rank N[1] and if it is applied dyadically, it is applied to sub-arrays of rank N[2] of and of N[3] of .
⎕←X←{f←⍺⍺ ⋄ ⍺←'' ⋄ '(',(⍕⍺(⎕CR'f')⍵),')'} ⋄ ⎕←(⊂X)⍤1 2 0⊢2 2⍴⎕A
 
@Adám
{f←⍺⍺ ⋄ ⍺←'' ⋄ '(',(⍕⍺(⎕CR'f')⍵),')'}
(   ⊂  AB )
(   ⊂  CD )
 
6:45 PM
I.e. applies to rank-1 sub-arrays.
⎕←X←{f←⍺⍺ ⋄ ⍺←'' ⋄ '(',(⍕⍺(⎕CR'f')⍵),')'} ⋄ ⎕←(819⌶2 2⍴⎕A)(⊂X)⍤1 2 0⊢2 2⍴⎕A
 
@Adám
{f←⍺⍺ ⋄ ⍺←'' ⋄ '(',(⍕⍺(⎕CR'f')⍵),')'}
( ab  ⊂ A)
( cd     )

( ab  ⊂ B)
( cd     )


( ab  ⊂ C)
( cd     )

( ab  ⊂ D)
( cd     )
 
I.e. applies to rank-2s of (which happens to be the entire array here) and rank-0s of .
Finally, let's explore how f∘g works. Any ideas for illustrating that?
 
Well, f∘g applies differently depending on ⍺⍵ so I don't know how to illustrate it properly
 
How about (again with a slightly modified X):
⎕←X←{f←⍺⍺ ⋄ ⍺←'' ⋄ ∊'('⍺(⎕CR'f')⍵')'} ⋄ ⎕←(,X)∘(⊂X)'⍵' ⋄ ⎕←'⍺'(,X)∘(⊂X)'⍵'
 
@Adám
{f←⍺⍺ ⋄ ⍺←'' ⋄ ∊'('⍺(⎕CR'f')⍵')'}
(,(⊂⍵))
(⍺,(⊂⍵))
 
6:55 PM
Here is an example of how we can use this to analyse more complex trains, like this CamelCase splitter:
⎕←(⊢⊂⍨∊∘⎕A)'CamelCaseRocks'
 
@Adám
┌─────┬────┬─────┐
│Camel│Case│Rocks│
└─────┴────┴─────┘
 
(I know the isn't necessary, but it is in there for illustration purposes.)
⎕←X←{f←⍺⍺ ⋄ ⍺←'' ⋄ ∊'('⍺(⎕CR'f')⍵')'} ⋄ ⎕←(⊢X⊂X⍨∊∘⎕A X)'⍵'
 
@Adám
{f←⍺⍺ ⋄ ⍺←'' ⋄ ∊'('⍺(⎕CR'f')⍵')'}
((∊∘ABCDEFGHIJKLMNOPQRSTUVWXYZ⍵)⊂(⊢⍵))
 
So now we can see how works and how is distributed to the outer functions.
And for an even more complex train, which splits on any number of delimiters:
⎕←' ,;'(⊢⊆⍨∘~∊⍨)'some delimiters;in,use'
 
@Adám
┌────┬──────────┬──┬───┐
│some│delimiters│in│use│
└────┴──────────┴──┴───┘
 
7:00 PM
⎕←X←{f←⍺⍺ ⋄ ⍺←'' ⋄ ∊'('⍺(⎕CR'f')⍵')'} ⋄ ⎕←'⍺'((⊢X)(⊆X)⍨∘(~X)(∊X)⍨)'⍵'
 
@Adám
{f←⍺⍺ ⋄ ⍺←'' ⋄ ∊'('⍺(⎕CR'f')⍵')'}
((~(⍵∊⍺))⊆(⍺⊢⍵))
 
Now we just have to note the obvious that ⍺⊢⍵ is .
This should also explain why and can get you the arguments when in a train.
I hope this lesson was useful. See you next week for multi-APL threading!
 
@Adám indeed it was. Looking forward to breaking stuff with multithreading
 
 
1 hour later…
8:07 PM
@Adám ×⍵ → 0× what?
 
@dzaima Sorry, fixed.
 
8:23 PM
@Adám you + cows quack have golfed a fifth off from my answer :p
 
@dzaima :-) My tentative solution is currently at 76.
 
@Adám oh you already have a solution
 
@EriktheOutgolfer Yeah, but I wanted you guys to have a chance.
 
@Adám eh, I'm not golfing that thing anymore. I have already wasted too much time not doing homework :p
 
Btw, someone should do FizzBuzz:
117
Q: 1, 2, Fizz, 4, Buzz

Beta DecayIntroduction In our recent effort to collect catalogues of shortest solutions for standard programming exercises, here is PPCG's first ever vanilla FizzBuzz challenge. If you wish to see other catalogue challenges, there is "Hello World!" and "Is this number a prime?". Challenge Write a progra...

 
9:02 PM
@Adám there's already an APL solution on that one
 
@Uriel Sure, but we can do better!
 
@Uriel it's GNU APL though
 
Adám has added an event to this room's schedule.
 
 
1 hour later…
10:37 PM
@Adám so, I finally made (or I hope so) a dfn to answer the challenge, but it's, uh, 101 bytes long
{G,⍨⊖⌽↑Y,¨,∘⊖∘⍕¨S@{'-'≠Y[⍵]}⍳⍴Y←'-'@{0=#0,5|2↓⍳⍴⍵}⍴∘S≢G←⊖G⍪⍴∘S{5-5|⍵}@0⍴1↓G←⍉{⍺,⍴∘'#'≢⍵}⌸⍵[⍋⍵]~S←' '}
claims ownership
 
@EriktheOutgolfer Here's mine:
{⊖r,h↑⍨≢r←⌽↑⊃,/¯1⌽¨@1⊢5↑¨{⊂⌽'-',⍨⍕⍵}¨1+@1⊢5×0,⍳⌈5÷⍨≢1↓h←⍉{⍺,∊⍕¨×⍵}⌸⍵[⍋⍵]∩⎕A}
 
@Adám oh, and mine assumes ⎕IO←0
 
@EriktheOutgolfer Crazy how much work it is to get that Y-axis right. The histogram itself is trivial.
 
@Adám actually, those two parts are kind of interleaved in my code
 
@EriktheOutgolfer How so? You make G first, which is the histogram.
 
10:43 PM
@Adám but it's not fully rotated before a later step (G←⊖)
 
@EriktheOutgolfer OK, I also flip as the last step.
 
@Adám hm, now that makes me wonder if I have been needlessly flipping a lot of times and not just done a grand flip
eh, well, it's past 01:00 where I live anyway :P
@Adám OK so now it looks like I'm down to 98
{⊖,∘G⌽↑Y,¨,∘⊖∘⍕¨S@{'-'≠Y[⍵]}⍳⍴Y←'-'@{0=#0,5|2↓⍳⍴⍵}⍴∘S≢G⍪⍴∘S{5-5|⍵}@0⍴1↓G←⍉{⍺,⍴∘'#'≢⍵}⌸⍵[⍋⍵]~S←' '}
however, it's invalid!
the error happens at the ,∘G part, while the shapes match perfectly (try removing ⊖,∘G to see that they are)
...or do they?
ah, looks like they were not, back to 100 bytes:
{⊖,∘G⌽↑Y,¨,∘⊖∘⍕¨S@{'-'≠Y[⍵]}⍳⍴Y←'-'@{0=#0,5|2↓⍳⍴⍵}⍴∘S≢G←G⍪⍴∘S{5-5|⍵}@0⍴1↓G←⍉{⍺,⍴∘'#'≢⍵}⌸⍵[⍋⍵]~S←' '}
 
@EriktheOutgolfer No they don't. 'hello' gives G a height of 3 and a the Y-axis a height of 6.
 
@Adám yeah ninja'd by a bit
 
@EriktheOutgolfer I'm exploring a new approach to the axis.
 
10:55 PM
looks like I didn't store the padding (multiple of 5, as specified in the challenge)
btw the Y,¨,∘⊖∘⍕¨S@{'-'≠Y[⍵]}⍳⍴Y←'-'@{0=#0,5|2↓⍳⍴⍵}⍴∘S part seems too redundant to me
it feels like I can combine the two @s into one
 
@EriktheOutgolfer My new approach also uses one @ for each of the numbers and the dashes.
 
06:00 - 23:0023:00 - 00:00

« first day (441 days earlier)      last day (2223 days later) »