10. # file: input.cr
name = gets
puts "Hello #{name.upcase} !"
$ crystal build input.cr
Evitar errores en runtime
11. # file: input.cr
name = gets
puts "Hello #{name.upcase} !"
$ crystal build input.cr
In input.cr:3:20
3 | puts "Hello #{name.upcase} !"
^-----
Error: undefined method 'upcase' for Nil (compile-time type is (String | Nil))
Evitar errores en runtime
12. Anotaciones de tipos (methods)
def greet(h)
n = h.name
puts "Hey #{n}! How are you #{n}?"
end
humans = [Human.new("Hiccup")]
greet(humans.first)
13. def greet(h : Human)
n : String
n = h.name
puts "Hey #{n}! How are you #{n}?"
end
humans = [Human.new("Hiccup")] of Human
greet(humans.first)
Anotaciones de tipos (methods)
14. Anotaciones de tipos (methods)
def greet(h)
...
humans = [] of Human
greet(humans.first) # (Runtime) Index out of bounds (IndexError)
greet(humans.first?) # (Compile) undefined method 'name' for Nil
def greet(h : Human)
...
greet(humans.first) # (Runtime) Index out of bounds (IndexError)
greet(humans.first?) # (Compile) no overload matches 'greet' with type
(Human | Nil)
15. class Dragon
def meet(h : Human)
puts "Bite"
end
def meet(d : Dragon)
puts "Play"
end
end
class Human
def meet(h : Human)
puts "Hi #{h.name}, I'm #{name}"
end
def meet(d : Dragon)
puts "Watch & train #{d.name}"
end
end
Multi-dispatch & “duck-typing”
creatures = [Human.new("Hiccup"), Human.new("Astrid"),
Dragon.new("Toothless"), Dragon.new("Fireworm")]
a, b = creatures.sample(2) # => a, b : Human | Dragon
print "#{a.name} meeting #{b.name}: "
a.meet(b)
16. class Human
@name : String
def initialize(name)
@name = name
end
def name
@name
end
end
Anotaciones de tipos (classes)
class Human
def initialize(@name : String)
end
def name
@name
end
end
19. channel = Channel(Int32).new
total_lines = 0
files = Dir.glob("*.cr")
files.each do |f|
spawn do
lines = File.read(f).lines.size
channel.send lines
end
end
files.size.times do
total_lines += channel.receive
end
puts total_lines
Concurrencia
● Fibers (coroutines)
● Managed thread(s) worker(s)
● Blocking API (no callbacks)
“Do not communicate by sharing memory;
instead, share memory by communicating.”
Effective Go
https://golang.org/doc/effective_go.html#sharing
20. class Object
macro property(name)
@{{name.var}} : {{name.type}}
def {{name.var}} : {{name.type}}
@{{name.var}}
end
def {{name.var}}=(@{{name.var}} : {{name.type}})
end
end
end
Metaprogramación
class Human
property name : String
def initialize(@name)
end
end
21. Integración con C
// C
double cos(double x);
double y = cos(1.5);
# Crystal
lib C
fun cos(x : Float64) : Float64
end
y = C.cos(1.5)
@[Link("pcre")]
lib LibPCRE
type Pcre = Void*
fun compile = pcre_compile(
pattern : UInt8*,
options : Int,
errptr : UInt8**,
erroffset : Int*,
tableptr : Void*) : Pcre
end
22. Elecciones en Crystal
● Syntaxis amena
● Compilado
● Evitar errores en runtime cuando se pueda
● Multi-dispatch
● Estáticamente tipado pero con inferencia y “duck-typing”
● Promover buenas prácticas de uso de recursos
● Modelo de programación concurrente
● Metaprogramación
● Integración con C
23. ● from a DB to JSON with Crystal
○ https://manas.tech/blog/2017/01/16/from-a-db-to-json-with-crystal.html
○ https://github.com/crystal-lang/crystal-db
● https://kemalcr.com/
● https://amberframework.org/
● https://luckyframework.org
● samples/2048.cr https://github.com/crystal-lang/crystal/tree/master/samples
● sdl raytracer https://github.com/asterite/crystal_sdl2_examples
● nes https://github.com/asterite/nes.cr
Apps & Frameworks