last day (399 days later) » 

Wow, that was fast.
Mkay, forked.
Hello everybody!
Let's see how ugly your perl is :P
01:27
It's just Java right now.
what
Ugly by default.
Well I guess you might as well stick with Java.
The only primitive are numbers currently?
It's not too late to switch to Perl. This is literally the same stuff I had when I asked about it.
Yes.
@PhiNotPi Oh, OK.
Are you going to do it OO style in Perl or..?
01:30
I'm definitely feeling OO for this project.
ok just make sure you remember how to tie scalars
:P
Phi what's up with your indentation
It's all over the place
are you mixing tabs and spaces?
I haven't mixed tabs and spaces, I mixed copy-paste and file upload.
Oh
That's problematic
Do you not have git?
I have git. I just typically use the online interface.
01:35
Ah OK
@quartata I honestly don't even know that that does.
I've done little-to-none OO in Perl.
It was kinda sort of a joke but anyways
If you haven't done a lot of OO in Perl you might not want to do it OO style like that
OO is... weird... in Perl.
Well, not exactly weird.
Just a little strange at first.
It was really an afterthought.
I know Perl was my original vision, but I just don't see myself being able to make this project in it.
That's fine.
You can stick with Java, I can still help
But please fix your indentation :P
2 or 4 spaces?
01:44
Whichever you prefer. I use 2
@quartata indention unborked
I might as well take this time to explain how everything works.
First, you launch the interpreter, which just takes your line of input from STDIO and feeds it into the Parser.
The Parser takes the string and returns a TokenList representing the program.
01:54
Right.
I figured that much out
The parser is just a switch-case for now right?
Basically.
The TokenList stores an ArrayList of Tokens, with the last token of the program first.
It also has the all-magical recursive eval() method.
oooooh
I've probably already mentioned this (multiple times, probably), but Phigs actually does its evaluation in reverse: looks at the end of the program to see how many arguments the operator takes, and then works backwards until it accumulates that number of arguments.
First, it removes the operator (the first token).
Then, it has a list of arguments, which starts empty.
It also has a list of "used" (consumed) tokens.
It takes the current list of arguments, and calls the Token's canEval(args) method.
This is it asking "do I currently have enough arguments to perform this operation"
If the answer is no, then it looks through its token list to find where the consumed tokens end, and the remaining unused tokens begin.
So it's prefix like Pyth in a sense
It makes a new TokenList using those remaining tokens, and recurses.
It's probably close to prefix in implementation.
The idea was: I want to be able to program in it like a stack-based language, but there's a great advantage in having the operator read before its arguments.
02:06
I see.
are stacks really that popular?
I mean, non-stack languages seem better to me
The original golfing language GolfScript was stack-based
i know
but
I'm considering just reversing the way Phigs is written to make it a prefix language.
05AB1E out-performs Pyth at most things so.
@PhiNotPi No, don't.
The benefit of this is that something like swap is essentially an adverb
But it makes more intuitive sense
Because it's modifying the stack as opposed to modifying how the function responds
I do have a suggestion though
Add an input variable _ and when you don't have enough arguments for a function, pad the stack with _
pl does this.
and it rocks
02:10
That's something I've already considered, and will probably add in.
It works really really well.
6
A: Catalan Numbers

quartatapl, 4 bytes ☼ç▲÷ Try it online. Explanation In pl, functions take their arguments off the stack and push the result back onto the stack. Normally when there are not enough arguments on the stack, the function simply fails silently. However, something special happens when the amount of argume...

Like about that well
I remember seeing that.
If you're not using Perl, you're going to have to figure out a system to auto-coerce strings to ints/floats/booleans as needed
I eventually want to have support for lambda expressions and other cool things.
02:32
Have I spammed you with enough suggestions yet? ;)
ok
Explanation of suspend/restore if you're curious:
in 05AB1E, Mar 6 at 16:02, by Aqua Tart
Suppose the stack is 0 1 2 3 and suspend/restore is $. 2$ removes the element at index 2 leaving 0 1 3. Then suppose time passes and the stack is now 0 1 3 4 5. Calling $ again restores 2 to where it was (index 2) giving 0 1 2 3 4 5.
I'll spam you with a few more suggestions
Suspend/restore might be more difficult in Phigs because we don't typically know the entire contents of the stack when we evaluate the operators.
How does swap work then? Is it dyadic?
yes
and it gives 2 results
02:40
Ah.
Does that make your comment here inaccurate?
33 mins ago, by quartata
The benefit of this is that something like swap is essentially an adverb
Yeah, it's a little different from what I thought.
I was thinking of it more like in the traditional stack-based sense: I presumed it was niladic and modified the stack directly.
Hmm, what else to suggest
How many suggestions have I even made? I've lost count
It is possible to make commands that operate on the entire stack, though.
@quartata 10 by my count
Oh, not as much as I thought.
Most of them you probably already thought of
Here's my idea for a map-like function.
02:51
This is what I meant by parallel map:
actually, there's a couple ways to do this...
basically you can pass n lists where n is the arity of the function you're mapping
it takes one element from each and passes it
if x, y, z are lists and M is map, then maybe xyzM*+ to do x+y*z
Oh, interesting. Like an implicit lambda.
I like that.
As for parallel for you can basically have x in array1, y in array2...
It'll iterate through all of them and end when it reaches the end of the smallest list
I'm trying to think through how M would work in my above example...
02:59
Well, I don't think it would quite work in that.
Actually
Wait
Hmm...
That's interesting.
When the program execution reaches M, it would have already seen the *+ so it would know that it would be expecting 3 lists as input.
But, then the issue is, how do I tell where the mapping stops?
You could have a terminating symbol }.
I was thinking instead of looking at the operators you'd look at how many arrays were available.
But that doesn't really work here.
As in, what if I don't want to map the + in xyzM*+
I could actually look at what lists are available.
That would be the best.
If you know that three lists are available you could just wrap the next three functions in a lambda and map that
What I'm wondering though is how we could fit currying into this. We'd have to choose between currying and implicit input, and it would be hard to parse in situations like this.
The way it works is... operators don't need to have fixed arity. It's not the case that they return a number of operands needed. Rather, each time a new operand is acquired, it asks whether the given list of operands is sufficient.
03:04
Right.
@quartata Can you give an example of currying in a situation like this?
@PhiNotPi Well, what if you had xM+
That would create a list of functions, essentially.
But the only way to know how to handle it properly is if you knew how many lists there were
Furthermore what if there were more lists on the stack but you wanted to curry
I'm thinking we'd have to make it explicit.
I think I remember thinking about this before.
IIRC, my solution was to have the map token (which was :) actually change some kind of flag on the array.
so xy+, xy:+, x:y:+ and x:y+ all did different things
 
10 hours later…
13:19
@quartata Regarding the whole "each time a new operand is acquired, it asks whether the given list of operands is sufficient" thing...
I could make it so that the program actually does look at the whole stack.
Traditional:
2 3 \ 5 * +   |
2             |  2
  3           |  2 3
    \         |  3 2
      5       |  3 2 5
        *     |  3 10
          +   |  13

Current:
2 3 \ 5 * +   |
          +   |  +
        * +   |  + *
      5 * +   |  + * 5
        * +   |  + * 5
    \   * +   |  + * 5 \
  3 \   * +   |  + * 5 \ 3
    \   * +   |  + * 5 \ 3
2   \   * +   |  + * 5 \ 3 2
    \   * +   |  + * 5 2 3
        * +   |  + 10 3
          +   |  13

Proposed:
2 3 \ 5 * +   |
          +   |  +
        * +   |  + *
13:55
The benefit of this is that stuff like suspend/restore would work.
The downside is that we lose some contextual information: being able to know what the first argument of a function is before even looking at the second argument.
One second trying to parse all this
@PhiNotPi How would suspend/restore fit into this?
Would it be varity?
Varity?
Variable arity.
i.e would it just take the whole stack
Yes
Well, almost everything (including stuff like multiplication, etc) would take the whole stack and just modify part of it.
Yeah.
Hm.
14:08
So, other than parsing from right to left, it is then evaluated left to right.
Yeah, I don't like that.
Here's what I'm thinking
stupid enter key
I think we should go for a mix
Would it be possible to make some operators wait until stack information is available and modify the whole stack?
We could have swap and co. be like that
Yes, that is possible.
OK, then we just have the rest be like the way we had them originally.
Hmm, although..
Will that screw up things like pop?
That would change how many arguments the next function gets.
I don't think it would mess up pop
OK.
Well, the other thing I was thinking
Was the adverb idea
We could make pop and swap be adverbs that modify the next function.
So something like \+ actually is one function
When the function is actually executed, the \ goes first and just changes the order of the arguments as appropriate
14:19
There's two ways of doing pop: arity of 1 that gives no result, or getting the entire stack and removing the top before passing it to the next function.
Hmm, how would this work with niladic functions....
Here's how it would work....
But niladic functions take no arguments, so there's nothing for the adverb to modify.
`\`, when executed, puts a new type of primitive, a Flag, on the stack
Whenever the Flag ends up being the argument of a function, then we perform that operation.
I think that could be messy though.
Because there's not a limit as to the number of swaps that can occur before the next operation.
Example: program is 2 3 \ 5 +
When we reach +, the stack is 2 3 \ 5. Normally it takes the top 2 arguments, but these are \ 5, so it knows to perform the \ on the remainder of the stack (2 3) to get 3 2 5 after pre-processing. The + then gives a result of 3 7.
That's an interesting idea
But like I said
What if you have a niladic function
The \ never ends up as an argument
14:28
As in, something like a literal 3?
Yeah.
Then the \ just remains buried in the stack, to be used sometime in the future when a function does use it
But what if you have something like _ DUPLICATE 2+ "spooky" \ "me"?
That's from an actual challenge mind you
I think the solution might be an identity function but that adds bytes
I would assume the implicit output would take the entire stack as an argument and carry out any \ inside of it.
We should probably stick to \ and pop being "regular functions"
 
3 hours later…
17:13
How much should I distinguish between lists and arrays?
Well.
I think the default "list/array" type should be a Java ArrayList
It doesn't make a whole lot of sense to have static size arrays in this case
 
2 hours later…
19:25
Phigs> [3[4 5]6]7
[3 [4 5] 6] 7
Let there be lists!
Phigs> [3 5] 2 *
[6 10]
Phigs> [4 6] [11 20] *
[44 120]
Phigs> 4 [1 3 [4 5]] *
[4 12 [16 20]]
My implementation of [ as a primitive can allow for some weirder stuff:
Phigs> 6 [\]
[6]
20:03
@PhiNotPi hahahaha
@PhiNotPi So it auto vectorizes?
@quartata I adjusted all the dyadic math functions to be "recursive" over lists.
Yeah, that's called vectorizing.
Then yes.
It works like that in APL/J/Jelly too
I'm not sure I quite get the last one
The 6 [\]
It pushes a 6 and then a [ onto the stack, and then swaps them. The ] looks down through the stack for the matching ] and groups the contents into a list.
IDK if that's a useful feature or not

  last day (399 days later) »