Survey
* Your assessment is very important for improving the workof artificial intelligence, which forms the content of this project
* Your assessment is very important for improving the workof artificial intelligence, which forms the content of this project
Introduction to Ruby Sebastian Fischer Part I •Data Numbers, Strings, Ranges, Arrays/Hashes •Control Branching, Loops, Iterators Numbers >> => >> => >> => 42 42 -17 -17 1.23 1.23 >> => >> => >> => 4.56e7 45600000.0 2.34e-4 0.000234 2.34>0 true >> => >> => >> => 17e-1.round 2 17/4 4 17./ 4 4 Strings >> => >> => >> => >> => >> => hello = "hello" "hello" world = "world" "world" hello = "#{hello} #{world}!" "hello world!" hello.chop! "hello world" hello "hello world" Escape >> => >> => >> => >> => "hello\nworld!" "hello\nworld!" 'hello\nworld!' "hello\\nworld!" "hello#{17+4}world!" "hello21world!" 'hello#{17+4}world!' "hello\#{17+4}world!" Regular Expressions >> => >> => >> => >> => >> => hello =~ /\s\w+/ 5 hello[5,6] " world" hello[5..10] " world" hello.gsub!(/\s\w+/,'\&!') "hello world!" hello "hello world!" Ranges >> => >> => >> => 1..3 1..3 (1..3).first 1 (1..3).last 3 >> => >> => >> => (1..3).member? 3 true (1..3).member? 4 false (1..3).entries [1, 2, 3] Arrays >> => >> => >> => >> => >> => a = [1,true,"huh?"] [1, true, "huh?"] a[2] "huh?" a.length 3 a + [42] [1, true, "huh?", 42] a * 2 [1, true, "huh?", 1, true, "huh?"] Arrays >> => >> => >> => >> => (a*2)[2..4] ["huh?", 1, true] (a*2)[2,3] ["huh?", 1, true] a[-1] "huh?" a[-2] true Hashes >> => >> => >> => >> => >> => >> => h = { 1 => true, "huh?" => 2.34 } {1=>true, "huh?"=>2.34} h[1] true h["huh?"] 2.34 h[true] nil h[true] = 42 42 h {true=>42, 1=>true, "huh?"=>2.34} Symbols >> => >> => >> => >> => :foo :foo :foo.to_i 14609 :foo.id2name "foo" "foo".to_sym :foo Data •Numbers •Strings, Regular Expressions •Ranges •Arrays •Hashes If, Unless >> => >> => >> => >> => if 3>0 then 42 else 87 end 42 42 if 3>0 42 unless 3>0 then 42 else 87 end 87 87 unless 3>0 nil Case >> >> >> >> >> >> => case i when 1, 2..5 "one to five" when 6..10 "six to ten" end "six to ten" >> => >> => >> >> >> >> >> >> => case "abcdef" when "abc" ,"def" "abc or def" when /def/ "includes def" end "includes def" (6..10) === 8 true /def/ === "abcdef" true While >> => >> >> >> >> => fac5 = 1; n = 1 1 while n <= 5 fac5 = fac5 * n n = n+1 end; fac5 120 While while (<condition>) { label_redo: <body> label_next: } label_break: Until >> => >> >> >> >> => fac5 = 1; n = 1 1 until n > 5 fac5 = fac5 * n n = n+1 end; fac5 120 For/in >> >> >> >> => fac5 = 1; for n in 1..5 fac5 = fac5 * n end; fac5 120 Iterators >> => >> => >> => fac5 = 1 1 (1..5).each { |n| fac5 = fac5 * n } 1..5 fac5 120 Iterators >> "hello".each_byte { |b| puts b } 104 101 108 108 111 => "hello" >> "hello\nworld!".each { |l| puts l } hello world! => "hello\nworld!" Iterators >> (1..3).each{ |n| print n } 123=> 1..3 >> [1,2,3].each{ |n| print n } 123=> [1, 2, 3] >> h.each{ |k,v| puts "#{k} => #{v}" } true => 42 1 => true => {true=>42, 1=>true} Iterators >> 3.times { puts "hello" } hello hello hello => 3 >> 1.upto(3) do |n| ?> puts n >> end 1 2 3 => 1 Control •if, unless •case •while, until, for/in •Iterators Part II •Classes and Objects Inheritance, Methods, Access Control •Accessor Methods •Modules Classes >> >> >> >> >> >> => class Person def initialize name @name = name end end me = Person.new "Sebastian" #<Person:0x362180 @name="Sebastian"> Classes class Man < Person def initialize name super name @gender = :male end end class Woman < Person def initialize name super name @gender = :female end end Objects >> me = Man.new "Sebastian" => #<Man:0x356588 @gender=:male, @name="Sebastian"> >> me.@name SyntaxError: compile error >> me.name NoMethodError: undefined method `name' for #<Man:0x356588 @gender=:male, @name="Sebastian"> Accessor Methods class Person def name @name end def name=(n) @name = n end end class Person attr_accessor :name end Accessor Methods >> => >> => >> => me.name "Sebastian" me.name = "Horst" "Horst" me #<Man:0x356588 @gender=:male, @name="Horst"> Modules module WithGender attr_reader :gender end class Man include WithGender end class Woman include WithGender end Reader Methods >> me.gender => :male >> me.gender = :female NoMethodError: undefined method `gender=' for #<Man:0x356588 @gender=:male, @name="Horst"> Singleton Methods >> >> >> => >> => >> => def me.gender=(g) @gender = g end nil me.gender = :female :female me #<Man:0x356588 @gender=:female, @name="Horst"> Modules module Student @@nr = 0 attr_reader :nr def next_nr @@nr += 1 end private :next_nr end Mixin class MaleStudent < Man include Student def initialize name super name @nr = next_nr end end class FemaleStudent < Woman include Student ... end Accessor Methods >> axel = MaleStudent.new "Axel" => #<MaleStudent:0x3631d4 @name="Axel", @nr=1 @gender=:male> >> rita = FemaleStudent.new "Rita" => #<FemaleStudent:0x361294 @name="Rita", @nr=2, @gender=:female> >> axel.gender => :male >> rita.nr => 2 Extending Classes >> >> >> >> >> >> => >> => class Integer def fact return 1 if self==0 self * (self-1).fact end end nil 5.fact 120 Class Hierarchies >> => >> => >> => >> => >> => 5.class Fixnum Fixnum.superclass Integer Integer.superclass Numeric Numeric.superclass Object Object.superclass nil Classes are Objects >> => >> => >> => >> => >> => Integer.class Class Class.class Class Class.superclass Module Module.class Class Module.superclass Object “Global” Functions >> >> >> => >> => >> => >> => def square x x*x end nil self.methods.select {|m| m =~ /sq/ } ["square"] 42.methods.select {|m| m =~ /sq/ } ["square"] "".square 7 49 Scope >> ["a","b","c"].each {|str| print str} abc=> ["a", "b", "c"] >> str NameError: undefined local variable or method `str' for main:Object >> str = "z" => "z" >> ["a","b","c"].each {|str| print str} abc=> ["a", "b", "c"] >> str => "c" Variables •Constants uppercase: Math::PI •Global Variables dollar sign: $PROGRAM_NAME Constants >> => >> => >> => Object.constants ["IO", "Student", ...] Student.constants [] WithGender.constants [] Prettier Objects module Student def inspect str = "Student: #{nr}" str += ", Name: #{name}" \ if respond_to? :name str += ", Gender: #{gender}" \ if respond_to? :gender str end end Prettier Objects >> axel => Student: 1, Name: Axel, Gender: male >> puts axel #<MaleStudent:0x365470> => nil Prettier Objects >> class Person >> def to_s; inspect end >> end >> puts axel Student: 1, Name: Axel, Gender: male => nil Exceptions class Person def name=(n) raise "name must not be empty!" \ if n.empty? @name = n end end >> me.name = "" RuntimeError: name must not be empty! Exceptions >> begin ?> me.name = "" >> puts 'name was set to ""' >> rescue >> puts "could not set name" >> ensure ?> puts "finished" >> end could not set name finished => nil Useful Stuff >> 5.f 5.floor 5.freeze 5.frozen? >> 5.f >> 5.methods => ["%", "inspect", ...] 5.fact Useful Stuff $ ri Array#each -----------------------------Array#each array.each {|item| block } -> array --------------------------------------Calls _block_ once for each element in _self_, passing that element as a parameter. ... Ruby will teach you to express your ideas through a computer. You will be writing stories for a machine. http://poignantguide.net/ruby/ Part III •Object#send •Method#call •Kernel#eval Object#send >> => >> => >> => "hello world".send :length 11 "hello world".send "length" 11 "hello".send :<<, " world" "hello world" Method#call >> => >> => >> => "hello world".method(:length).call 11 app = "hello".method :<< #<Method: String#<<> app.call(" world") "hello world" Kernel#eval >> => >> => >> eval '"hello world".length' 11 eval '"hello" << " world"' "hello world" eval 'system "rm *"' Module#class_eval class Module def my_attr_reader sym class_eval "def #{sym}()" << " @#{sym} end" end def my_attr_writer sym class_eval "def #{sym}=(v)" << " @#{sym}=v end" end end Attribute Accessors class Klass my_attr_reader :a my_attr_reader :b my_attr_writer :b def initialize() @a=42 end end Attribute Accessors >> => >> => >> => >> => klass = Klass.new #<Klass:0x353784 @a=42> klass.a 42 klass.b = 17 17 klass.b 17 http://www.ruby-doc.org/docs/ProgrammingRuby/