如何“或”数组范围内的所有元素

时间:2016-10-14 15:15:03

标签: arrays ruby indexing

我想在一行if x == consonants[0] or [1] or [2][21]consonants[0..21]。出于某种原因,我认为consonants = ["b", "c", "d", "f", "g", "h", "j", "k", "l", "m", "n", "p", "q", "r", "s", "t", "v", "w", "x", "y", "z"] new_first = ["m", "a", "t", "t", "h", "e", "w", "s"] new_first.each do |x| if x == consonants[0] puts x.next! elsif x == consonants[1] puts x.next! elsif x == consonants[2] puts x.next! elsif x == consonants[3] puts x.next! else puts "test failed" end end 会起作用,但事实并非如此:

$(function () {
  $('#thedialog').dialog({
    autoOpen: false,
    hide: 'fold',
    show: 'blind',
    position: {
      my: "center", 
      at: "center",
      of: window.top
    },
    open: function (event, ui) {
      setTimeout(function () {
        $('#thedialog').dialog('close'); 
      }, 2000) }
   });
});

5 个答案:

答案 0 :(得分:4)

有几种方法可以解决这个问题,但这取决于您的性能问题,以及这需要的可扩展性。通常情况下,ifx == y形式的x == z语句链可以折叠成:

 case (x)
 when y, z
   # ... Executed on a match
 end

在您的情况下,您甚至可以通过将数组用作有效值列表来执行此操作:

 case (x)
 when *constants
   puts x.next!
 end

对于较大的列表,您可能希望将其折叠成一个Set,因为它们针对include?测试进行了优化:

consonants_set = Set.new(consonants)

if (consonants_set.include?(x))
  puts x.next!
end

由于您正在进行单字母匹配,因此您有更多选择。例如,正则表达式:

consonants_regexp = Regexp.new('[%s]' % consonants.join)

if (consonants_regexp.match(x))
  puts x.next!
end

或者您甚至可以进行简单的子串匹配:

consonants_string = consonants.join

if (consonants_string[x])
  puts x.next!
end

值得注意,但你可以遍历字符串中的字符:

'cwzbrly'.each_char do |c|
  puts c
end

这样就无需创建和/或输入[ 'a', 'b', ... ]形式的长数组。

答案 1 :(得分:0)

你可以这样做:

if consonants.include? (x)
     your-code-here
end

这将检查数组中是否有等于x的元素。

答案 2 :(得分:0)

您可以使用正则表达式

if x =~ /[aeiou]/
  puts 'test failed'
else
  puts x.next!    
end

/[aeiou]/表示匹配任何a,e,i,o或u。

这将消除创建辅音数组的需要。

答案 3 :(得分:0)

如果我正确理解并且您期望nuuixt因此,您可以这样做:

new_first.select { |letter| consonants.include?(letter) && letter.next! }

&&以这种方式工作:如果consonants.include?(letter)的计算结果为true,则阻止返回letter.next!

答案 4 :(得分:0)

考虑一下:

consonants = ('a' .. 'z').to_a - %w[a e i o u] # => ["b", "c", "d", "f", "g", "h", "j", "k", "l", "m", "n", "p", "q", "r", "s", "t", "v", "w", "x", "y", "z"]
shifted_consonants = consonants.zip(consonants.rotate).to_h # => {"b"=>"c", "c"=>"d", "d"=>"f", "f"=>"g", "g"=>"h", "h"=>"j", "j"=>"k", "k"=>"l", "l"=>"m", "m"=>"n", "n"=>"p", "p"=>"q", "q"=>"r", "r"=>"s", "s"=>"t", "t"=>"v", "v"=>"w", "w"=>"x", "x"=>"y", "y"=>"z", "z"=>"b"}
'matthews'.chars.map{ |c| shifted_consonants[c] || c } # => ["n", "a", "v", "v", "j", "e", "x", "t"]

'a'范围转换为'z'并将其转换为数组,然后减去元音数组,只产生辅音。

接下来,它将辅音数组转换为哈希/查找表shifted_consonants,其中每个键都是当前辅音,值是下一个辅音。

最后,它会占用'matthews'中的每个字符,并查看该字符的shifted_consonants中是否有值。如果不是,则返回nil,触发||并返回当前字符。如果散列中有一个匹配,则返回该辅音的下一个值,这会使||“或”短路。

替代方案是利用tr

consonants = (('a' .. 'z').to_a - %w[a e i o u]).join # => "bcdfghjklmnpqrstvwxyz"
shifted_consonants = consonants.chars.rotate.join # => "cdfghjklmnpqrstvwxyzb"
'matthews'.tr(consonants, shifted_consonants).chars # => ["n", "a", "v", "v", "j", "e", "x", "t"]

检查速度:

CONSONANTS = ('a' .. 'z').to_a - %w[a e i o u] # => ["b", "c", "d", "f", "g", "h", "j", "k", "l", "m", "n", "p", "q", "r", "s", "t", "v", "w", "x", "y", "z"]
SHIFTED_CONSONANTS_HASH = CONSONANTS.zip(CONSONANTS.rotate).to_h # => {"b"=>"c", "c"=>"d", "d"=>"f", "f"=>"g", "g"=>"h", "h"=>"j", "j"=>"k", "k"=>"l", "l"=>"m", "m"=>"n", "n"=>"p", "p"=>"q", "q"=>"r", "r"=>"s", "s"=>"t", "t"=>"v", "v"=>"w", "w"=>"x", "x"=>"y", "y"=>"z", "z"=>"b"}

CONSONANTS_STR = (('a' .. 'z').to_a - %w[a e i o u]).join # => "bcdfghjklmnpqrstvwxyz"
SHIFTED_CONSONANTS_STR = CONSONANTS_STR.chars.rotate.join # => "cdfghjklmnpqrstvwxyzb"

require 'fruity'

sample_string = 'matthews'
compare  do
  use_hash { sample_string.chars.map{ |c| SHIFTED_CONSONANTS_HASH[c] || c } }
  use_tr { sample_string.tr(CONSONANTS_STR, SHIFTED_CONSONANTS_STR).chars }
end

# >> Running each test 2048 times. Test will take about 1 second.
# >> use_tr is faster than use_hash by 10.000000000000009% ± 10.0%

样本字符串越长,差异越大。改为:

sample_string = 'matthews' * 1000

我看到的结果是:

# >> Running each test 4 times. Test will take about 1 second.
# >> use_tr is faster than use_hash by 4x ± 0.1

在评论中找到, NOT 在它所属的问题中......

  

我的目标是将constonant更改为下一个辅音,并将元音更改为arraynew_first = [“m”,“a”,

的下一个元音

调整这里的一些变化。你可以解开增量:

ALPHABET = ('a' .. 'z').to_a
VOWELS = %w[a e i o u]
CONSONANTS = ALPHABET - VOWELS # => ["b", "c", "d", "f", "g", "h", "j", "k", "l", "m", "n", "p", "q", "r", "s", "t", "v", "w", "x", "y", "z"]

SHIFTED_CONSONANTS = CONSONANTS.rotate # => ["c", "d", "f", "g", "h", "j", "k", "l", "m", "n", "p", "q", "r", "s", "t", "v", "w", "x", "y", "z", "b"]
SHIFTED_VOWELS = VOWELS.rotate # => ["e", "i", "o", "u", "a"]

SHIFTED_CONSONANTS_HASH = CONSONANTS.zip(SHIFTED_CONSONANTS).to_h # => {"b"=>"c", "c"=>"d", "d"=>"f", "f"=>"g", "g"=>"h", "h"=>"j", "j"=>"k", "k"=>"l", "l"=>"m", "m"=>"n", "n"=>"p", "p"=>"q", "q"=>"r", "r"=>"s", "s"=>"t", "t"=>"v", "v"=>"w", "w"=>"x", "x"=>"y", "y"=>"z", "z"=>"b"}
SHIFTED_VOWELS_HASH = VOWELS.zip(SHIFTED_VOWELS).to_h # => {"a"=>"e", "e"=>"i", "i"=>"o", "o"=>"u", "u"=>"a"}

sample_string = 'matthews'

sample_string.chars.map{ |c| SHIFTED_CONSONANTS_HASH[c] || SHIFTED_VOWELS_HASH[c] } # => ["n", "e", "v", "v", "j", "i", "x", "t"]


CONSONANTS_STR = CONSONANTS.join # => "bcdfghjklmnpqrstvwxyz"
SHIFTED_CONSONANTS_STR = SHIFTED_CONSONANTS.join # => "cdfghjklmnpqrstvwxyzb"
SHIFTED_VOWELS_STR = SHIFTED_VOWELS.join # => "eioua"
CHARACTERS_STR = (CONSONANTS + VOWELS).join # => "bcdfghjklmnpqrstvwxyzaeiou"
SHIFTED_CHARACTERS_STR = SHIFTED_CONSONANTS_STR + SHIFTED_VOWELS_STR # => "cdfghjklmnpqrstvwxyzbeioua"

sample_string.tr(CHARACTERS_STR, SHIFTED_CHARACTERS_STR).chars # => ["n", "e", "v", "v", "j", "i", "x", "t"]

这些更改不会影响实际代码的速度:tr仍然无法使用哈希查找。