Skip to content

Instantly share code, notes, and snippets.

@xaviervia
Last active December 29, 2015 19:19
Show Gist options
  • Save xaviervia/7716401 to your computer and use it in GitHub Desktop.
Save xaviervia/7716401 to your computer and use it in GitHub Desktop.
Pika brainstorming

Pika Showdown:

hello-world.pika

# Just prints "Hello World!"
print("Hello World!")
> pika hello-world
Hello World!
> pika help hello-world
Just prints "Hello World!"

greeter.pika

# Greets the Master
person |
print("Greetings " + person)
> pika greeter Xavier
Greetings Xavier
> pika help greeter
Greets the Master

- person

invoker.pika

# Invokes the greeter with fixed argument
greeter: require("greeter.pika")
greeter("Magneto")
> pika invoker
Greetings Magneto

documenter.pika

# Shows the invokers.pika documentation
invoker: require("invoker.pika")
print(invoker comments)
> pika documenter 
Invokes the greeter with the fixed argument

cat.pika

# Creates a Cat from a Mammal prototype
Mammal: {
  walk: {
    print("Your mammal is walking")
  }
}

Cat: Mammal()
Cat walk()
> pika cat
Your mammal is walking

tortoise.pika

# Creates a Tortoise from a partially filled
# prototype Reptile, created in time from
# Animal
name|

Animal: {legs, species, name|
  walk: {
    print("Your " + species + " " + name + " is walking on " + legs + "legs")
  }
}

Reptile: Animal(4)

Tortoise: Reptile("Tortoise")

Tortoise("Donatello") walk()
> pika tortoise
Your Tortoise Donatello is walking on 4 legs

conditional.pika

# Makes a conditional statement
# Note that "if" is just a function!
temperature|
if(temperature greater(20), {
  print("Nice weather")
}, {
  print("Getting cooler")
})
> pika conditional 14
Getting cooler
> pika conditional 25
Nice weather

return.pika

# There is no return statement in pika
# Only callbacks
number|
multiplier: {value, callback|
  callback(value * 7)
}
multiplier(number, {result|
  print(result)
})
> pika return 8
56

sugar.pika

# Buuut you are allowed to some syntactic sugar
#
# The 'x' as the second argument is actually a 
# reserved word and means "assign callback 
# value instead of call instance"
number|
3times: {value, callback| 
  callback(value * 3)
}

result: 3times(number, x)
print(result)
> pika sugar 4
12

jump.pika

# Every execution of a pika environment
# returns that execution as an instance
#
# Partial executions (some arguments are
# missing) mean that the block of the function
# is not evaluated: only properties are assigned
jump: {person, object|
  print(person + " jumped the " + object)
}
aJump: jump("Oscar", "fridge")
print(aJump person)
print(aJump)
> pika jump
Oscar jumped the fridge
Oscar
{ person: "Oscar", object: fridge, print(person + " jumped the " + object)}

argumentable.pika

# Functions can provide an "argumentable object"
# experience
name|

missingName: {name, height: 1.74|}
solved: missingName(name)
print(solved)
> pika argumentable Jan
{ name: "Jan", height: 1.74 }

pipe.pika

# The pipe as operator only means that
# declared variables before the pipe
# are required unless stated otherwise
#
# Variables declared after the pipe can be
# assigned as arguments but are not
# required for the calls in the block
# to be executed. 
#
# Tip: Variables declared after the pipe
# are optional arguments
Measures: {height, width|
  depth
}

cube: Measures(10, 10, 10)
sheet: Measures(29, 21)
print(cube)
print(sheet)

# The sheet can still be extruded!
extrude: sheet(5)
print(extrude depth)
> pika pipe
{ height: 10, width: 10, depth: 10 }
{ height: 29, width: 21}
5

dot.pika

# The dot operator references the current 
# context. Two dots represents the parent
# context. This is useful to defined properties
# on the parent.
#
# Because there is no "self" or "this" in Pika
chimera: {
  wingify: {howMany|
    ..wings: howMany
  }
}

chimera wingify(2)
print(chimera wings)
> pika dot
2

override.pika

# Variables are naturally overriden in the
# inner contexts. If not specified by "." or ".."
# or "..." (etc), the variables match the inner declaration.
# 
# Declarations in inner contexts do not affect the outside
#
# This is most useful for exception handling. A basic
# try-catch implementation
raise: {message|
  print("Oh my! " + message)
  quit()
}

try: {block, fallback| 
  raise: {message|
    # The "." to reference the raise instance... 
    # the "error" object in traditional programming
    fallback(.) 
  }

  block()
}

# Then you can capture an exception
try({
  raise("Thunderstorm!")
},{captured|
  print("I stopped this: " + captured message)
})

# ...and you can also give it the look and 
# feel of a somewhat more regular try catch by taking 
# advantage of partial executions
catch: try({
  raise("Tsunami!")
})

catch({captured|
  print("Dammed the " + captured)
})
> pika override
I stopped this: Oh My! Thunderstorm!
Dammed the Oh My! Tsunami!

japan.ピカ

# You can clone anything. If the arguments
# are not exhausted, you can clone anything
# just by executing it.
#
# For example, lets internationalize the 
# "if" method
si: if()
om: if()
если: if()

# Lets get Japanese (google translated, don't judge)
# 20 is of course an object
20 大きい: 20 greater()
もし: if()
印刷: print()

# We can add a condition clause via property 
# without affecting the regular "if"
もし condition: 20 大きい(10, x)

# And check if it is true
もし({
  印刷("ピカは素晴らしいです!")
})
> ピカ japan
ピカは素晴らしいです!

duplicate.pika

# If the arguments have all been assigned
# and you still want to duplicate the object
# without executing its block, there is a hack: 
# add an argument and do not fill it!
#
# Will add a "template" argument.
#
# Of, I forgot to mention: arguments are just `fillable`
# properties of the objects. Fillable is 
# a primitive represented by an `O`
#
# No strange chars in Pika!
toDuplicate: {|
  print("This should not be printed!")
}

toDuplicate template: O

clone: toDuplicate()

# You can remove the template property if you want
toDuplicate delete("template")
clone delete("template")

# Boureaucratic. But works

async.pika

# You can make asynchronous calls. It's easy
> read("file.txt", {filename, contents|
  print(filename + " has been read")
})

# Synchronous would be just
read("file.txt", {filename, contents| 
  print("Read again synchronously")
})
> pika async.pika
file.txt has been read
Read again synchronously

later.pika

# Tidier code, but synchronous
readings: read("bigfile.txt", x)

# Asynchronous wildness
readings > read("bigfile.txt", later)
print(later)

# "readings" is an instance, but "later"
# is a "promise": will actually be completed later
# 
# A synchronous call to "done" in the reading 
# instance will execute the block when later is loaded
readings done({
  print(later)
})
> pika later
{ filename: "bigfile.txt", contents: O}
{ filename: "bigfile.txt", contents: <...> }

array.pika

# Pika accepts arrays. They are actually objects
# with numbers as property names.
#
# Tip: most Pika is syntactic sugar over a very
# simple program structure
array: ["y", "z"]

array 2: "a"

print(array)
> pika array
["y", "z", "a"]

kindness.pika

# Want to intercept multiple callbacks?
# Does not matter why, Pika allows you
kindness: {animal, good, great|
  good("Feed " + animal)
  great("Take care of " + animal)
} 

options = kindness("Ted", x, x)
print(options)
> pika kindness
{ good: "Feed Ted", great: "Take care of Ted" }

asterisk.pika

# Any string can be used as variable name, 
# including string with spaces. To be able to use
# strings as variable names as arguments, you can
# explicit their pointer status by using the *

# When in the left side of ":" or after another
# variable, its status of property name is clear
rice: {
  "cook some cups": {amount|

  }
}
"the water": "is great"

print(*"the water")
> pika asterisk
is great
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
OSZAR »