Best of Ruby Quiz 笔记之二: LCD numbers

quiz2 LCD 数字

关键字:数组操作 行列转换

题目意图:输出类似LCD风格的数字,内容由命令行参数决定,并根据"-s"命令行参数指定其大小

思路:
需要的method
1) 转换方法,将正常的数字,转换为LCD风格的数字
2) 缩放方法,缩放LCD风格的数字
3) 处理命令行参数方法,读取输入的数字和给定的"-s"参数

笔记:
1、transpose
arr.transpose -> an_array
假设 arr是一个由数组组成的数组,并调换其行和列
a = [ [1,2], [3,4], [5,6] ]
a.transpose -> [[1,3,5], [2,4,6]]
2、
DIGITS = <<END_DIGITS.split("\n").map { |row| row.split(" # ") }.transpose
 -  #    # -  # -  #    # -  # -  # -  # -  # -
| | #  | #  | #  | #| | #|   #|   #  | #| | #| |
    #    # -  # -  # -  # -  # -  #    # -  # -
| | #  | #|   #  | #  | #  | #| | #  | #| | #  |
 -  #    # -  # -  #    # -  # -  #    # -  # -
END_DIGITS

将上面的字符串进行如下处理后转成数组
1) 按换行符号"\n"拆分为数组
2) 对数组中每个元素按"#"拆分为数组,并置回原数组中
3) 此时的数组形为[ [" -  ", "    "," -  ",...], ["|  | ", ...], [...], ... ] 共5个元素,每个元素都是包含十个元素的数组,
对大数组进行transpose操作后,大数组变为有十个元素,分别是0-9的lcd风格的数字显示。每个元素都是有5个元素的数组,并且这个5个元素构成一个lcd风格的数字显示,5个元素对应5行。

3、row = line.dup
dup obj.dup->other_obj
生成obj的一个浅拷贝--拷贝了obj的实例变量,但是没有拷贝他引用的对象。dup拷贝了obj的tainted (是否受信)状态。同时可参加Object#clone的描述。一般而言,在派生类中clone和dup或许有不同的语义。一般使用clone来复制一个对象以及它的内部状态,而dup通常使用派生对象的类来创建新的实例。

4、scale方法说明
def scale( num, size )
 bigger = [ ]
 num.each do |line|         # 作为参数传进来的num其实就是一个数字的lcd显示,此处针对其5行字符做处理
  row = line.dup        
  row[1, 1] *= size        # row[1,1]指向下标为1,并且取1个长度的元素的组合,这个元素有可能是"-"或空格,
                  # 该元素总是应该随着size变化的
  if row.include? "|"       # 包含"|"的行,需要纵向缩放
   size.times { bigger << row }
  else
   bigger << row         # 不包含"|"的行,只要处理横向缩放,即"-"和空格即可
  end
 end                # 缩放完成
 bigger              # 返回缩放后的数组
end

5、shift
arr.shift->obj 或nil
返回arr的第一个元素,并将它从数组中删除(其他元素左移一个位置)。如果数组为空,返回nil
args = ["-m", "-q", "filename"]
args.shift -> "-m"
args -> ["-q", "filename"]

6、n.each_byte do |c| ……
each_byte 把str中的每个字节传入给定的block

7、zip
enum.zip(<arg>) ->array
enum.zip(<arg>){|arr|block} -> nil
把参数转成数组,然后将enum中的元素和每个参数中对应的元素合并起来。结果是一个和enum具有相同数目元素的数组。其中的每个元素是一个含有n个元素的数组,此处的n比参数个数大1。如果任意一个参数的元素个数小于enum的元素个数,则使用nil。如果带有block,则以每个输出的数组为参数进行调用,否则返回由结果数组组成的数组。

a = [4, 5, 6]
b = [7, 8, 9]
(1..3).zip(a, b)   -> [[1, 4, 7], [2, 5, 8], [3, 6, 8]]
"cat\ndog".zip([1]) -> [["cat\n", 1], ["dog", nil]]
(1..3).zip   -> [[1],[2],[3]]

在LCD_number.rb中,
num = ([""] * (s * 2 + 3)).zip(*num)
将num这个数组的元素做一次行列转换,,转为有s*2+3个元素的数组,每个数组元素包含每行应显示的字符

/Files/bryanzk/LCD_number.rar

posted on 2007-07-18 17:00  小熊bryan  阅读(547)  评论(0编辑  收藏  举报