介绍
就像许多其他编程语言一样,Ruby中也有Map方法。一般来说,你使用ruby map或map来转换数据,并对对象的每个元素执行功能。你可以将其用于哈希、范围和数组。所有这些都是以地图作为Enumerable对象来工作的。让我们深入到本指南中,了解更多关于ruby map方法的信息。
带索引的地图
Ruby中没有直接的 "map_with_index "方法。取而代之的是,你可以做一个这样的 :
my_array = [:mouse, :bat, :pangolin]
newly_created_array = my_array.each_with_index.map { |value, index| "The #{value} is at position #{index}" }
# => ["The mouse is at position 0", "The bat is at position 1", "The pangolin is at position 2"]
在这个例子中,my_array
是保持原样的。
不出所料,each_with_index
方法返回一个二维数组。
my_array = [:mouse, :bat, :pangolin]
newly_created_array = my_array.each_with_index.to_a
# => [[:mouse, 0], [:bat, 1], [:pangolin, 2]]
另一个很好的可能性,也可能是更直观的方式来实现 "带索引的映射",如下所示(从Ruby 1.9开始)。
my_array = [:mouse, :bat, :pangolin]
newly_created_array = my_array.map.with_index { | value, index | "The #{value} is at position #{index}" }
# => ["The mouse is at position 0", "The bat is at position 1", "The pangolin is at position 2"]
现在我们已经看到了如何用索引进行映射,让我们回到基础知识上来。
Ruby地图方法--基本理解
一个Ruby地图方法有一个可枚举的对象(你要调用地图方法的对象)和一个块。对于对象的每一个元素,map都会执行块,并对其应用该特定的功能。map返回一个数组作为结果,这个数组是由评估块的结果构建的。一旦你看到这个语法,它就会开始对你有意义了。
Ruby地图方法 - 语法
Ruby Map方法的语法非常简单。比方说,你的可枚举对象是一个数字数组。那么它将简单地看起来像my_array.map
。语法的这一部分之后是块,它被定义在两个大括号内{}
。
你在这个{}
块内定义函数和任务。你定义你想如何转换my_array
中的每个元素。例如,你想把数组中的每个元素都乘以2。然后,你将通过在块内声明一个变量来定义它。请看下面这段代码。
my_array = [1, 2, 3]
p my_array.map { |n| n * 2 } # |n| -> declaring a variable, n*2 performing the function
# output: [2, 4, 6]
现在你对ruby map有了基本的了解,让我们看看更多的例子来具体了解。
例子 - Ruby Map
如果你熟悉ruby中的功能,你可以简单地在map中定义它们,并将其用于你的优势。例如,让我们使用ruby map方法将一个字符串数组转换成一个整数数组。
使用Ruby Map将一个字符串数组转换为一个整数数组
my_array = ["10","9","8"]
p my_array.map {|str| str.to_i}
# output: [10, 9, 8]
to_i
是用于将字符串转换为整数的函数。
在字符串数组上使用Map
你也可以使用map将字符串的每个元素转换为大写。
my_array = ["x", "y", "z"]
p my_array.map { |string| string.upcase }
# output: [X, Y, Z]
在哈希上使用Map
让我们来看看一个有点复杂的例子。我们也可以在散列上使用地图。我们都知道,哈希包含一个键值对。所以,在这种情况下,基本上有两个参数而不是一个。我们将不得不定义两个变量,我们将能够对哈希中存在的每个键值对执行功能/转换。 在下面的例子中,我们使用to_sym
,将哈希的每个元素转换为一个符号。
hash = { protein: "Meat", fruit: "orange" }
p hash.map { |k,w| [k, w.to_sym] }
# output: [[:protein, :Meat], [:fruit, :orange]]
在前面的例子中,我们已经了解到map以数组的形式返回一个结果。正如你在上面的代码例子中所看到的,map返回了一个数组。一个多维数组。一个数组的一个元素包含两个元素。那么,我们怎样才能得到我们所需要的哈希值呢?请看下面的例子。
hash = { protein: "Meat", fruit: "orange" }
p hash.map { |k,w| [k, w.to_sym] }.to_h
# => {:protein=>:Meat, :fruit=>:orange}
正如你所看到的,仅仅通过简单地写to_h
,它是用来将对象转换成哈希值的,我们将地图上的结果数组转换成哈希值。
你也可以使用ruby maps来执行以下任务。
c = [18, 22, 3, 3, 53, 6]
p c.map {|num| num > 10 }
# => [true, true, false, false, true, false]
p c.map {|num| num.even? }
# => [true, true, false, false, false, true]
上面的代码例子已经很清楚了。在第一个map方法中,你正在检查数组中的元素是否大于10。那么输出应该是不言自明的。在第二个映射方法中,你正在检查数组中的哪些元素是偶数。
带有索引的Ruby Map
如果你想让结果数组显示出索引,你可以通过使用with_index
方法简单地做到这一点。让我们来看看这个代码例子。
my_array = ["a","b", "c"]
p my_array.map.with_index { |ch, idx| [ch, idx] }
# output: [["a", 0], ["b", 1], ["c", 2]]
############
my_array = [10, 50, 100]
p my_array.map.with_index { |ch, idx| [ch, idx] }
# output: [[10, 0], [50, 1], [100, 2]]
############
my_array = %w(1 2 3)
p my_array.map.with_index { |ch, idx| [ch, idx] }
# output: [["1", 0], ["2", 1], ["3", 2]]
正如你所看到的,with_index
,可以用于任何数据类型。使用这个方法,地图将生成一个带有索引的结果数组。看一下最后一个例子。my_array = %w(a b c)
,你一定注意到这里有什么不寻常的地方。%w
是一个创建字符串的快捷方式。如果你看到输出,你会发现结果数组的值是字符串数据类型。
Ruby Map vs Each
你可以说.each
只是.map
的一个基本版本。它的工作原理与 Ruby Map 相同。唯一的区别是,它不收集结果。在.each
的情况下,结果数组将始终保持不变,并处于其原始状态。这意味着在每种情况下,它都不收集结果。另一方面,.map
具有相同的功能,但它收集和存储结果数组。
my_array = [1, 2, 3]
p my_array.each { |n| n * 2 }
# [1, 2, 3]
p my_array.map { |n| n * 2 }
# [2, 4, 6]
请注意,原始数组是不变的。
Ruby Map vs Collect
Ruby.map
和.collect
碰巧是同一目的的不同名称。它们被用于相同的功能和任务。但是总的来说,.map
更加常用。
最后的思考
在本指南中,你学会了对ruby地图的基本理解。现在是时候让你多多练习了。好好掌握它的功能,并尝试在不同的编程任务中使用它。