Як дізнатися, чи починається рядок з іншої рядки в Ruby?


Відповіді:


254
puts 'abcdefg'.start_with?('abc')  #=> true

[редагувати] Це те, чого я не знав до цього питання: start_withбере кілька аргументів.

'abcdefg'.start_with?( 'xyz', 'opq', 'ab')

1
МРТ 1.8.7 не має start_with?, але МРТ 1.9 робить, як і Рейки.
Уейн Конрад

@Wayne Конрад: Як не дивно, 1.8.7 дійсно є документація для String#start_with?.
Йорг W Міттаг

@ Йорг W Міттаг, можливо, не дивно, я помилявся. МРТ 1.8.7 насправді є start_with?. Я думаю, я написав це, коли завантажував irb, щоб спробувати.
Уейн Конрад

7
Цікаво, що Rails визначає граматично правильно starts_with?, що в 1.8.7 і вище просто псевдонім start_with?.
Марк Томас

56

Оскільки тут представлено кілька методів, я хотів з’ясувати, який із них був найшвидшим. Використання Ruby 1.9.3p362:

irb(main):001:0> require 'benchmark'
=> true
irb(main):002:0> Benchmark.realtime { 1.upto(10000000) { "foobar"[/\Afoo/] }}
=> 12.477248
irb(main):003:0> Benchmark.realtime { 1.upto(10000000) { "foobar" =~ /\Afoo/ }}
=> 9.593959
irb(main):004:0> Benchmark.realtime { 1.upto(10000000) { "foobar"["foo"] }}
=> 9.086909
irb(main):005:0> Benchmark.realtime { 1.upto(10000000) { "foobar".start_with?("foo") }}
=> 6.973697

Таким чином, схоже, що start_with?ist найшвидший з цієї групи.

Оновлені результати за допомогою Ruby 2.2.2p95 та новішої машини:

require 'benchmark'
Benchmark.bm do |x|
  x.report('regex[]')    { 10000000.times { "foobar"[/\Afoo/] }}
  x.report('regex')      { 10000000.times { "foobar" =~ /\Afoo/ }}
  x.report('[]')         { 10000000.times { "foobar"["foo"] }}
  x.report('start_with') { 10000000.times { "foobar".start_with?("foo") }}
end

            user       system     total       real
regex[]     4.020000   0.000000   4.020000 (  4.024469)
regex       3.160000   0.000000   3.160000 (  3.159543)
[]          2.930000   0.000000   2.930000 (  2.931889)
start_with  2.010000   0.000000   2.010000 (  2.008162)

4
не дивно, що давати компіляцію та тестування на регулярні вирази набагато складніше, ніж просто порівняння байтів
akostadinov

1
Слід зазначити, що Regex набагато кращий за нечутливим пошуком випадків, навіть якщо ви обчислили всі перестановки випадків для тестового рядка достроково.
Пітер П.

3
@PeterP. Я щойно перевіряв нечутливі пошукові запити та start_with? по- , як і раніше виходить вперед , якщо ви просто downcase рядки для пошуку , а потім порівняти з пошуковим рядком малих літер: "FooBar".downcase.start_with?("foo").
haslo

4

Метод, згаданий Steenslag, є лаконічним, і зважаючи на обсяг питання, його слід вважати правильним. Однак також варто знати, що цього можна досягти за допомогою регулярного вираження, яке, якщо ви ще не знайомі з Рубі, є важливим навиком для навчання.

Пограйте з Rubular: http://rubular.com/

Але в цьому випадку наступний оператор ruby ​​повернеться true, якщо рядок зліва починається з 'abc'. \ A в прямому знаку регулярного вираження означає "початок рядка". Пограти з рубуляром - стане зрозуміло, як все працює.

'abcdefg' =~  /\Aabc/ 

Як зауважив Уейн Конрад, цей метод також буде працювати на більш широкому спектрі виконання, ніж стартує start_with.
pakeha

Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.