Những kiến thức thường gặp dành cho các Ruby Developer mới (Part 2)

Giới thiệu

Hôm nay, mình xin giới thiệu tiếp về những kiến thức cở bản và cần thiết dành cho các Ruby Developer mới. Bạn có thể xem lại bài Part 1 ởi link này https://viblo.asia/p/nhung-kien-thuc-thuong-gap-danh-cho-cac-ruby-developer-moi-part-1-gAm5yxVXldb.

Part 1 mình đã giới thiệu những kiến thức cần thiết như: instance variables, class variables, modules, cách sử dụng extend, include, các class và object .... Hôm này mình sẽ giới thiệu tiếp như sau:

Symbols

Khác với ngôn ngữ lập trình khác, Ruby có một kiểu variable được gọi là Symbol. Để tạo symbol, chúng ta dùng : ở trước các từ khác như::name, :@foo, ... Symbol có thể dùng để đặc trưng cho tên method, instance variables và constants. ví dụ:

worker = {
  :name => "John Doe",
  :age => "35",
  :job => "Basically Programmer"
}

puts worker[:name] # => "John Doe"

Blocks, Procs, and Lambdas

Method calls trong Ruby có thể dùng {...} hoặc do ... end ỏ sau nó. ví dụ

[1,2,3].each { |i| print i }  
hoặc
[1,2,3].each do |i| 
    print i 
end

Những code ở giữa được gọi là block.

Storing Blocks

Ruby blocks có thể gán hoặc lưu giá trị của nó ở trong 2 container: Procs và Lamdas. Mình có thể so sánh việc store này giống như anonymous functions của javascript, tức là mình không cần tạo method, mình có thể tạo các blocks và gán luôn cho biến nào đó. Có nhiều các để dùng Procs và lambdas như sau:

// Procs
add = Proc.new {|a, b| a + b}
// Lambdas
add = lambda {|a, b| a + b} 
// hoặc 
add = -> (a, b) {a + b}

Để thực hiện, mình dùng hàm #call

puts add.call 1, 2 # => 3

Scope Resolution Operator (:😃

Một vấn đề có thể xảy ra khi bạn có tên module hoặc class giống với tên của core Ruby module. ví dụ

module MyModule
  class File
  end

  class Thing
    def exist?(path)
      File.exist?(path)
    end
  end
end

thing = MyModule::Thing.new
thing.exist?('/etc/hosts') # => udefined method `exist?' for MyModule::File:Class

Để fix lỗi này, bạn cần dùng :: operator ở trước tên mà bị trùng ấy như sau:

module MyModule
  class File
  end

  class Thing
    def exist?(path)
      ::File.exist?(path)
    end
  end

end

thing = MyModule::Thing.new
thing.exist?('/etc/hosts') # => true

Tạo hash từ list của các values

Nếu bạn có danh sách các giá trị, bạn hoàn toàn tạo thành hash bằng sử dụng Hash[...]

Hash['key1', 'value1', 'key2', 'value2']
# => {"key1"=>"value1", "key2"=>"value2"}

Double Pipe Equals ||=

Đây là một kỹ thuật viết rất dơn giản và có ích. Cách viết này thuòng dùng để cache lại kết quả mà đã tính toán hoặc đã thực hiện rồi, tránh việc tính toán hoặc thực hiện lại. Nó sẽ đảm bảo là hàm đó chỉ chạy đúng một lần đầu tiên.

def total
  @total ||= (1..100000000).to_a.inject(:+)
end

Khi mình gọi hàm total lần đầu, nó sẽ thực hiện tính toán. Nếu mình gọi lại một lần nữa, sẽ lấy giá trị đã có, không cần tính toán lại.

Conclusion

Qua 2 bài đã giới thiệu về những Tips quan trọng trong Ruby xong, mong các bạn sẽ hiểu được nhiều hơn. Chi tiết xem các tài liệu sau đây: https://devblast.com/b/ruby-tricks-improve-code https://www.sitepoint.com/common-trip-ups-new-rubyists/ http://www.rubyinside.com/21-ruby-tricks-902.html