Reputation: 13112
I want to reverse a string each two characters with Ruby.
The input:
"0123456789abcdef"
The output that I expect:
"efcdab8967452301"
Upvotes: 2
Views: 440
Reputation: 773
"0123456789abcdef".split('').each_slice(2).to_a.reverse.flatten.join('')
=> "efcdab8967452301"
Upvotes: 1
Reputation: 110665
I like all the solutions, especially @sawa's, but now, six hours later, its a challenge to come up with something different. In the interest of diversity, I offer a way that uses pairwise substitution. It's destructive, so I start by making a copy of the string.
Code
str = "0123456789abcdef"
s = str.dup
(0...s.size/2).step(2) { |i| s[i,2], s[-i-2,2] = s[-i-2,2], s[i,2] }
s #=> "efcdab8967452301"
Explanation
Letting
enum = (0...s.size/2).step(2) #=> #<Enumerator: 0...8:step(2)>
we can see what is enumerated:
enum.to_a #=> [0, 2, 4, 6]
The string
s #=> "0123456789abcdef"
is as follows after each call to the block:
i = 0: "ef23456789abcd01"
i = 2: "efcd456789ab2301"
i = 4: "efcdab6789452301"
i = 6: "efcdab8967452301"
Upvotes: 1
Reputation: 44675
You can try:
"0123456789abcdef".chars.each_slice(2).to_a.reverse.join
Upvotes: 2
Reputation: 168081
"0123456789abcdef".gsub(/../, &:reverse).reverse
# => "efcdab8967452301"
Upvotes: 3
Reputation: 13112
I'm not sure if this is the best way to do it:
"0123456789abcdef".scan(/../).reverse.join == "efcdab8967452301"
Upvotes: 3