里也使用了x.reduce的结果,并没有丢弃。
select()和select!()
filter()、filter!()分别等价于select()、select!()。
迭代数组,并从数组中选择那些符合语句块中测试条件的元素,最后组成一个新数组。
select()
不会修改原始数组对象,select!()
会修改原始对象。
arr = [1, 2, 3, 4, 5, 6]
new_arr = arr.select {|a| a > 3}
p new_arr # [4, 5, 6]
p arr # [1, 2, 3, 4, 5, 6]
new_arr = arr.select! {|a| a > 3}
p new_arr # [4, 5, 6]
p arr # [4, 5, 6]
reject()和reject!()
和select()是相反的行为,从数组中筛选不满足条件的元素。
reject()
不会修改原始数组对象,reject!()
会修改原始对象。
arr = [1, 2, 3, 4, 5, 6]
new_arr = arr.reject {|a| a > 3}
p new_arr # [1, 2, 3]
p arr # [1, 2, 3, 4, 5, 6]
new_arr = arr.reject! {|a| a > 3}
p new_arr # [1, 2, 3]
p arr # [1, 2, 3]
keep_if()
keep_if {|item| block} → ary
keep_if → Enumerator
keep_if()
从数组中删除不满足语句块中条件的元素,即保留满足条件的元素。
注意原处修改对象。
arr = [1, 2, 3, 4, 5, 6]
new_arr = arr.keep_if {|a| a < 4}
p new_arr # [1, 2, 3]
p arr # [1, 2, 3]
uniq()和uniq!()
ary.uniq -> new_ary
ary.uniq {|item| ...} -> new_ary
ary.uniq! -> ary or nil
ary.uniq! {|item| ...} -> ary or nil
对于语句块格式的语法,将迭代每个元素,然后根据语句块中的返回值作为重复值比较的依据。
对于uniq!(),如果没有任何重复元素可以去除,则返回nil,这时原数组不变,这是带有后缀!
但不改变原对象的一个特例。其它情况这些方法均返回去重后的数组。
a = [ "a", "a", "b", "b", "c" ]
a.uniq # ["a", "b", "c"], a不变
b = [["student","sam"], ["student","george"], ["teacher","matz"]]
b.uniq {|s| s.first} # [["student","sam"],["teacher","matz"]],b不变
a = [ "a", "a", "b", "b", "c" ]
a.uniq! # ["a", "b", "c"],a已变
b = [ "a", "b", "c" ]
b.uniq! # nil,b不变
c = [["student","sam"], ["student","george"], ["teacher","matz"]]
c.uniq! {|s| s.first} # [["student","sam"],["teacher","matz"]],c已变
compact()和compact!()
compact! → new_ary
compact! → ary or nil
去除数组中所有nil元素。
带感叹号的方法表示原处修改,如果没有nil元素可去除,则返回nil。
["a",nil,"b",nil,"c",nil].compact #["a","b","c"]
["a",nil,"b",nil,"c"].compact! # ["a","b","c"]
["a","b","c"].compact! # nil
all()、any()、none()和one()
all? [{ |obj| block } ] → true or false
all?(pattern) → true or false
any? [{ |obj| block } ] → true or false
any?(pattern) → true or false
none? [{ |obj| block } ] → true or false
none?(pattern) → true or false
one? [{ |obj| block } ] → true or false
one?(pattern) → true or false
对于这些方法,均有三种行为:
- 当使用语句块时,将判断容器中是否所有元素(all)、是否任一元素(any)、是否没有元素(none)、是否有且只有一个元素(one)满足语句块中的条件
- 当不使用语句块但给定参数时,将使用
===
的测试符号去判断容器中是否所有元素(all)、是否任一元素(any)、是否没有元素(none)、是否有且只有一个元素(one)满足条件
- 当不使用语句块且不给定参数时,将判断容器中是否所有元素(all)、是否任一元素(any)、是否没有元素(none)、是否有且只有一个元素(one)为true
需要特别对待的是空数组,虽然空数组自身是一个bool true,但空数组没有元素:
- 对于all(),空数组表示所有元素都为true,因为它根本没元素,所以返回true
- 对于any(),空数组表示没有元素为true,因为它根本没元素,所以返回false
- 对于none(),空数组表示没有元素为true,因为它根本没元素,所以返回true
- 对于one(),空数组没有一个元素为true,因为它根本没元素,所以返回false
# all()
%w[ant bear cat].all? { |word| word.length >= 3 } # true
%w[ant bear cat].all? { |word| word.length >= 4 } # false
%w[ant bear cat].all?(/t/) # false
[1,