`
simohayha
  • 浏览: 1400535 次
  • 性别: Icon_minigender_1
  • 来自: 火星
社区版块
存档分类
最新评论

ruby way之Arrays

    博客分类:
  • ruby
阅读更多
1 创建和实例化一个数组

类方法[]能够创建一个数组,这里有3种方法使用[]来创建一个数组:
a = Array.[](1,2,3,4)
b = Array[1,2,3,4]
c = [1,2,3,4]


这里还有一个方法叫做new也可以创建一个数组,它可以接受0,1或者2个参数,第一个参数是数组的大小,第二个参数是数组中每一个元素的默认值。

d = Array.new               # Create an empty array
e = Array.new(3)            # [nil, nil, nil]
f = Array.new(3, "blah")    # ["blah", "blah", "blah"]


这边要注意的是,上面的最后一个例子,这里虽然每个元素都有一个默认值,可是这些默认值指向的其实都是相同的对象。也就是说改变其中任何一个元素,剩下的元素都会改变。如果要产生出的默认值,每个都有一个对象,那就要使用一个block:

f=Array.new(3,"blah")
f[0].capitalize!            # f is now: ["Blah", "Blah", "Blah"]
puts f.to_s
g = Array.new(3) { "blah" } # ["blah", "blah", "blah"]
g[0].capitalize! 
puts g.to_s


2 存取和修改数组的元素

我们能够使用[]和[]=方法来存取数组中的元素,[]中可以放一个整数,一对整数或者一个区间。如果是负数的话就从最右边开始:

a = [1, 2, 3, 4, 5, 6]
b = a[0]                # 1
c = a.at(0)             # 1
d = a[-2]               # 5
e = a.at(-2)            # 5
f = a[9]                # nil
g = a.at(9)             # nil
h = a[3,3]              # [4, 5, 6]
i = a[2..4]             # [3, 4, 5]
j = a[2...4]            # [3, 4]

a[1] = 8                # [1, 8, 3, 4, 5, 6]
a[1,3] = [10, 20, 30]   # [1, 10, 20, 30, 5, 6]
a[0..3] = [2, 4, 6, 8]  # [2, 4, 6, 8, 5, 6]
a[-1] = 12              # [2, 4, 6, 8, 5, 12]


注意下面的例子,当我们想付给数组的元素太多时,将会发生什么:

k = [2, 4, 6, 8, 10]
k[1..2] = [3, 3, 3]     # [2, 3, 3, 3, 8, 10]
k[7] = 99               # [2, 3, 3, 3, 8, 10, nil, 99]
puts k.to_s

上面的例子可以看出,当元素太多时,数组会自动增长.

我们如果把一个数组付给一个数组元素,这时将会产生一个嵌套数组:

m = [1, 3, 5, 7, 9]
m[2] = [20, 30]         # [1, 3, [20, 30], 7, 9]

puts m.to_s
# On the other hand...
m = [1, 3, 5, 7, 9]
m[2..2] = [20, 30]      # [1, 3, 20, 30, 7, 9]
puts m.to_s


方法slice是[]方法的别名:
x = [0, 2, 4, 6, 8, 10, 12]
a = x.slice(2)               # 4
b = x.slice(2,4)             # [4, 6, 8, 10]
c = x.slice(2..4)            # [4, 6, 8]


方法first和last返回数组第一个和最后一个元素:

x = %w[alpha beta gamma delta epsilon]
a = x.first      # "alpha"
b = x.last       # "epsilon"


你如果想得到数组中某几个元素组成的数组,你可以使用values_at方法:

x = [10, 20, 30, 40, 50, 60]
y = x.values_at(0, 1, 4)        # [10, 20, 50]
z = x.values_at(0..2,5)         # [10, 20, 30, 60]


3 得到一个数组的大小

方法length和它的别名size能够返回一个数组的大小
x = ["a", "b", "c", "d"]
a = x.length               # 4
b = x.size                 # 4


方法nitems 也是返回数组的大小,不过他计算时不会包括nil的值:

y = [1, 2, nil, nil, 3, 4]
c = y.size                 # 6
d = y.length               # 6
e = y.nitems               # 4


4 比较数组

实例方法<=>被使用来比较两个数组,两个数组比较小于返回-1,等于返回0,大于返回1.方法==和!=依赖于<=>方法。

<=>方法的比较是一个元素一个元素进行,遇到相等的,就往下走:

a = [1, 2, 3, 9, 9]
b = [1, 2, 4, 1, 1]
c = a <=> b            #由于a[2]<b[2]所以a<b -1 (meaning a < b)


如果两个数组每一个对应元素都相等,那么这两个数组就相等,如果两个数组不一样长的话,那就只比到短的元素的结尾:

d = [1, 2, 4]
e = [1, 2, 3, 4]
f = [1, 2, 3]
puts d<=>e
puts d<=>f


由于array没有mix comparable模块,因此 <, >, <=, 和>=方法,并不能用,我们可以include comparable模块,就能使用这些方法了:

if a < b
  print "a < b"       # Prints "a < b"
else
  print "a >= b"
end
if d < e
  puts "d < e"        # Prints "d < e"
end


当两个不同类型的元素进行比较时就会报错:

d = [1, 2, "3"]
e = [1, 2, 3, 4]
f = [1, 2, 3]
class Array
  include Comparable
end
puts d<e #这边会出错,因为"3" <=>3 时,会报错


可是!=和=方法却是可以正常使用:

if g != h             # No problem here.
  puts "g != h"       # Prints "g != h"
end


可以看下下面的例子:
i = [1, 2, 3]
j = [1, 2, 3, "x"]
if i < j             # No problem here.
  puts "i < j"       # Prints "i < j"
end


这边可以清楚的看到,j的最后一个元素没有参与比较.

5排序一个数组

最简单的排序一个数组的方法是使用内置的sort方法:
words = %w(the quick brown fox)
list = words.sort  # ["brown", "fox", "quick", "the"]
puts list.to_s
# Or sort in place:
words.sort!        # ["brown", "fox", "quick", "the"]


sort方法假设数组里面没一个元素都是可比较的,因此比如[1, 2, "tHRee", 4]这样的数组,进行排序的话,就会报错.

我们还可以使用一种更灵活的排序方式,那就是使用sort的block版本:

a = [1, 2, "three", "four", 5, 6]
b = a.sort {|x,y| x.to_s <=> y.to_s}  #x,y分别是每次传进来的两个元素.
# b is now [1, 2, 5, 6, "four", "three"]
x = [1, 4, 3, 5, 2]
y = x.sort {|a,b| b <=> a}    # [5, 4, 3, 2, 1]


当我们想要根据很多key来排序的话,我们使用sort方法,就显得非常麻烦,这个时候我们能够使用Enumerable 模块的sort_by方法:
words=[1,2,"3"]
puts words.sort
puts lists =words.sort_by{|item| item.to_s}


如果是多个key我们就可以使用一个数组,这里假设数组list里的对象有name,age, height三个属性,我们想依次按照这3个key排序,我们就可以这样做:

list = list.sort_by {|x| [x.name, x.age, x.height] }


6 通过一定的规则来选择出元素

比如给定一个数组,我们想把这个数组中第一个的偶数取出来,这时我们可以使用detect 方法:

x = [5, 8, 12, 9, 4, 30]
#得到第一个偶数
x.detect {|e| e % 2 == 0 }         # 8
# 得到第一个7的倍数
x.detect {|e| e % 7 == 0 }         # nil


find 方法和detect是同意的,如果我们想得到这个数组中所有的偶数,这是就该使用find_all方法,而select和find_all方法是同意的:

# Continuing the above example...
x.find {|e| e % 2 == 0}            # 8
x.find_all {|e| e % 2 == 0}        # [8, 12, 4, 30]
x.select {|e| e % 2 == 0}          # [8, 12, 4, 30]


grep方法调用===方法来匹配数组中的每一个元素与他自己所带的参数.由于是使用===方法,因此grep方法的参数不需要是正则表达式:

a = %w[January February March April May]
a.grep(/ary/)      # ["January, "February"]
b = [1, 20, 5, 7, 13, 33, 15, 28]
b.grep(12..24)     # [20, 13, 15]


如果使用它的block版本的话,那就更灵活,这样可以再次处理所匹配的元素:

# Continuing above example...
# Let's store the string lengths
a.grep(/ary/) {|m| m.length}     # [7, 8]
# Let's square each value
b.grep(12..24) {|n| n*n}         # {400, 169, 225}


reject方法和select完全相反,看名字就知道了,它是选择不符合条件的:

c = [5, 8, 12, 9, 4, 30]
d = c.reject {|e| e % 2 == 0}    # [5, 9]
c.reject! {|e| e % 3 == 0}
# c is now [5, 8, 4]


min 和max方法,返回一个数组中的最大和最小值,没有block的事使用默认的比较,如果使用block,则是可以自定义:

a = %w[Elrond Galadriel Aragorn Saruman Legolas]
b = a.min                                 # "Aragorn"
c = a.max                                 # "Saruman"
d = a.min {|x,y| x.reverse <=> y.reverse} # "Elrond"
e = a.max {|x,y| x.reverse <=> y.reverse} # "Legolas"


index返回所传入的参数是数组元素的第几个元素:

i = a.index a.min     # 2
j = a.index a.max     # 3


7 使用数组作为数学的集合

ruby的数组能很好的支持数学的集合的操作,可是如果你想使用更好的,那你可以使用内置库里面的set方法:

a = [1, 2, 3, 4, 5]
b = [3, 4, 5, 6, 7]
c = a | b            # [1, 2, 3, 4, 5, 6, 7]
d = a & b            # [3, 4, 5]

#移除重复的元素..
e = [1, 2, 2, 3, 4]
f = [2, 2, 3, 4, 5]
g = e & f            # [2, 3, 4]


-是从一个集合里面去除掉另外一个集合里面含有的第一个集合里的东西:

a = [1, 2, 3, 4, 5]
b = [4, 5, 6, 7]
c = a - b            # [1, 2, 3] 注意没有6,7


array并没有定义异或操作,可是我们能够自己定义异或操作:

class Array

  def ^(other)
    (self | other) - (self & other)
  end

end

x = [1, 2, 3, 4, 5]
y = [3, 4, 5, 6, 7]
z = x ^ y            # [1, 2, 6, 7]

要检测一个元素是否属于一个集合我们能够使用include?或者member? :

x = [1, 2, 3]
if x.include? 2
  puts "yes"     # Prints "yes"
else
  puts "no"
end


我们如果要判断一个集合是否是另一个集合的子集合,尽管没有内置的方法,可是我们能够自己定义:

class Array

  def subset?(other)
    self.each  do |x|
      if !(other.include? x)
        return false
      end
    end
    true
  end

  def superset?(other)
    other.subset?(self)
  end

end

a = [1, 2, 3, 4]
b = [2, 3]
c = [2, 3, 4, 5]

flag1 = c.subset? a     # false
flag2 = b.subset? a     # true
flag3 = c.superset? b   # true


8 将一个数组随机显示,也就是打乱掉
我们可以使用kernel的rand方法.
class Array

  def randomize
    self.sort_by { rand }    # sort by a key which is a
  end                        #  random number

  def randomize!
    self.replace(self.randomize)
  end

end

x = [1, 2, 3, 4, 5]
y = x.randomize      # [3, 2, 4, 1, 5]
x.randomize!         # x is now [3, 5, 4, 1, 2]


9 多维数组

如果你想要使用多维数组,你可以使用NArray 库。

这边我们自己定义了一个三维数组:

class Array3

  def initialize
     @store = [[[]]]
  end

  def [](a,b,c)
    if @store[a]==nil ||
       @store[a][b]==nil ||
       @store[a][b][c]==nil
      return nil
    else
      return @store[a][b][c]
    end
  end

  def []=(a,b,c,x)
    @store[a] = [[]] if @store[a]==nil
    @store[a][b] = [] if @store[a][b]==nil
    @store[a][b][c] = x
  end

end


x = Array3.new
x[0,0,0] = 5
x[0,0,1] = 6
x[1,2,3] = 99

puts x[1,2,3] #我们现在能这样的存取多维数组,而不是x[1][2][3]


10找出在一个数组中而不在另一个数组中的元素

得到两个数组里面一个里面有,另一个数组没有的元素:
text = %w[the magic words are squeamish ossifrage]
dictionary = %w[an are magic the them these words]
# Find potential misspellings
unknown = text - dictionary   # ["squeamish", "ossifrage"]


11数组的变换或者映射

我们能够使用collect,方法来操作数组,她也就是和一般函数式语言里面的map函数一样,将会返回一个新的数组,正好ruby中也有map方法,它是collect方法的别名:

x = %w[alpha bravo charlie delta echo foxtrot]
# Get the initial letters
a = x.collect {|w| w[0..0]}        # 对每一个元素应用 [0..0] %w[a b c d e f]
# Get the string lengths
b = x.collect {|w| w.length}       # [5, 5, 7, 5, 4, 7]
# map is just an alias
c = x.map {|w| w.length}           # [5, 5, 7, 5, 4, 7]




12从一个数组移除掉一个nil的值

我么能使用compact方法:

a = [1, 2, nil, 3, nil, 4, 5]
b = a.compact     # [1, 2, 3, 4, 5]
a.compact!        # a is now [1, 2, 3, 4, 5]


13 删除掉重复的数组元素

我们能够使用delete_at方法来删除一个指定位置的元素:

a = [10, 12, 14, 16, 18]
a.delete_at(3)              # 删除 第三个元素(从0开始) Returns 16
# a is now [10, 12, 14, 18]
a.delete_at(9)              # Returns nil (out of range)


我们还能使用delete方法来删除一个指定的元素:

b = %w(spam spam bacon spam eggs ham spam)
b.delete("spam")            # Returns "spam"
# b is now ["bacon", "eggs", "ham"]
b.delete("caviar")          # Returns nil


delete还能跟上一个block,block的意思就是如果找不到那个元素就会返回block:

c = ["alpha", "beta", "gamma", "delta"]
c.delete("delta") { "Nonexistent" }
# Returns "delta" (block is never evaulated)
c.delete("omega") { "Nonexistent" }
# Returns "Nonexistent"


delete_if方法将会通过block来删除元素;

email = ["job offers", "greetings", "spam", "news items"]
# Delete  长度等于4的元素
email.delete_if {|x| x.length==4 }
# email is now ["job offers", "greetings", "news items"]


shift和pop方法,也能删除数组中的元素:
x = [1, 2, 3, 4, 5]
x.pop                   # Delete the last element
# x is now [1, 2, 3, 4]
x.shift                 # Delete the first element
# x is now [2, 3, 4]


clear方法将会删除一个数组中的所有元素。

14数组的拼接和附加

这个很简单,就看代码就行了:

x = [1, 5, 9]
x << 13        # x is now [1, 5, 9, 13]
x << 17 << 21  # x is now [1, 5, 9, 13, 17, 21]

x = [1,2]
y = [3,4]
z = [5,6]
b = y + z         # [3,4,5,6]
b += x            # [3,4,5,6,1,2]
z.concat y        # z is now [5,6,3,4]


15迭代一个数组

我么能够使用reverse_each 来反响迭代一个数组:

words = %w(Son I am able she said)
str = ""
words.reverse_each { |w| str += "#{w} "}
# str is now "said she able am I Son "


each_with_index 方法的block将会多出一个index参数,使我们更容易操作:

x = ["alpha", "beta", "gamma"]
x.each_with_index do |x,i|
  puts "Element #{i} is #{x}"
end
# Produces three lines of output


16转换成一个字符串

我们能够使用join方法:

been_there = ["Veni", "vidi", "vici."]
journal = been_there.join(", ")        # "Veni, vidi, vici."

letters = ["Phi","Mu","Alpha"]
musicians = letters.join(" ")          # "Phi Mu Alpha"

people = ["Bob","Carol","Ted","Alice"]
movie = people * " and "
# movie is now "Bob and Carol and Ted and Alice"


17反转一个数组

使用reverse 方法:

inputs = ["red", "green", "blue"]
outputs = inputs.reverse          # ["green","blue","red"]
priorities = %w(eat sleep code)
priorities.reverse!               # ["code","sleep","eat"]


18移除掉重复的元素

使用uniq方法:

breakfast = %w[spam spam eggs ham eggs spam]
lunch = breakfast.uniq   # ["spam","eggs","ham"]
breakfast.uniq!          # breakfast has changed now


19数组的交叉

我们想要交叉两个数组,合并为一个数组,我们可以使用zip方法:

a = [1, 2, 3, 4]
b = ["a", "b", "c", "d"]
c = a.zip(b)
# c is now [[1,"a"], [2,"b"], [3,"c"], [4,"d"]]
# Use flatten if you want to eliminate the nesting
d = c.flatten
# d is now [1, "a", 2, "b", 3, "c", 4, "d"]






























分享到:
评论

相关推荐

    PHP.Arrays.in.PHP.7

    Gain an in-depth understanding of PHP 7 arrays. After a quick overview of PHP 7, each chapter concentrates on single, multi-dimensional, associative, and object arrays. PHP Arrays is a first of its ...

    System.arraycopy和Arrays.copyOf

    `System.arraycopy` 和 `Arrays.copyOf` 都是Java中用于复制数组的方法,但它们在使用和处理异常情况上有所不同。这两个方法在处理数组复制时,提供了便利和效率,但各有其适用场景。 `System.arraycopy` 是一个...

    Antenna Arrays and Automotive Applications

    radar antenna arrays, and smart antenna arrays for automatic cruise control applications provide increased safe travelling for vehicle passengers. Vehicle localization techniques based on the antenna ...

    Collection与Collections,Array与Arrays的区别

    Collection与Collections,Array与Arrays的区别 Collection与Collections的区别: Collection是一个接口,位于java.util包下,是各种集合结构的父接口。它提供了最基本的集合操作,如add、remove、contains等。...

    PHP Arrays Single, Multi-dimensional, Associative and Object Arrays in 无水印原版pdf

    PHP Arrays Single, Multi-dimensional, Associative and Object Arrays in PHP 7 英文无水印原版pdf pdf所有页面使用FoxitReader、PDF-XChangeViewer、SumatraPDF和Firefox测试都可以打开 本资源转载自网络,如...

    Judy Arrays for Ruby-开源

    Judy Arrays for Ruby,或简称RJudy,就是这样一个工具,它引入了Judy Arrays库到Ruby环境中,为处理大量数据提供了高效、快速的方法。 Judy Arrays是一种特殊的数组结构,最初由JudyL和JudyHS两个C语言库实现。...

    图片url地址arrays.xml

    网络图片地址url集合arrays.xml文件

    Java中Arrays实用方法

    /** *Arrays提供数组操作的一系列实用方法 *1输出 *2排序 *3二分查找 *4复制 *5扩容 */

    Arrays

    NULL 博文链接:https://chaoyi.iteye.com/blog/2082720

    Electronically Scanned Arrays.pdf

    利用电磁波的相干原理,通过计算机控制输往天线各阵元电流相位的变化来改变波束的方向,同样可进行扫描,称为电扫描。天线阵,根据扫描情况可分为相扫、频扫、相/相扫、相/频扫、机/相扫、机/频扫、有限扫等多种体制...

    Microphone Arrays Signal Processing Techniques and Applications

    《麦克风阵列信号处理技术及其应用》是探讨麦克风阵列在语音信号处理领域中应用的权威书籍,涉及到的技术领域包括语音增强、声源定位和麦克风阵列的应用等方面。麦克风阵列技术主要利用多个麦克风收集声波信号,通过...

    你清楚Arrays.binarySearch()方法的返回值吗?

    在Java编程语言中,`Arrays`类是Java.util包下的一个非常重要的工具类,它提供了大量用于操作数组的静态方法,其中包括我们今天要讨论的`binarySearch()`方法。`Arrays.binarySearch()`方法允许我们在有序数组中查找...

    learn c the hard way

    14. switch语句(Switch Statement):深入讨论了switch语句的语法和它与if语句的不同之处。 15. 函数编写和使用(Writing And Using Functions):展示了如何编写自定义函数以及函数的调用。 16. 指针(Pointers...

    Antenna Arrays.pdf

    ### 天线阵列基础知识及设计变量 #### 天线阵列定义 天线阵列是一种将多个单个天线(元素)按照特定布局排列,从而实现特定辐射模式的配置方式。通过改变天线阵列的设计变量,可以精确地控制其辐射特性。...

    天线圣经- Finite Antenna Arrays and FSS

    天线圣经-Finite Antenna Arrays and FSS

    [PDF] Digital Signal Processing with Field Programmable Gate Arrays (part 1 of 4)

    《Digital Signal Processing with Field Programmable Gate Arrays》扫描版

    Electronically_Scanned_Arrays

    ### 相控阵天线(Electronically Scanned Arrays)详解 #### 一、引言与历史背景 相控阵天线(Electronically Scanned Arrays,ESA),是一种能够通过电子方式实现波束扫描和定位的天线系统,无需机械转动即可完成...

    LeetCode4 Median of Two Sorted Arrays

    There are two sorted arrays nums1 and nums2 of size m and n respectively. Find the median of the two sorted arrays. The overall run time complexity should be O(log (m+n)). Java AC版本

    numpy-numpy教程之Arrays的创建.zip

    本教程将深入探讨如何在NumPy中创建Arrays,这是理解NumPy基础的关键步骤。 一、NumPy概述 NumPy(Numerical Python)是Python的一个扩展程序库,主要用于处理大型多维数组和矩阵。它的设计目标是提供一种高效且...

Global site tag (gtag.js) - Google Analytics