2009-05-22 2 views
11

Я пытаюсь проанализировать многострочную строку и получить оставшуюся часть строки после шаблона.Что такое «рубиновый путь» для синтаксического анализа строки для одного ключа/значения?

текст:

 
hello john 
your username is: jj 
thanks for signing up 

Я хочу, чтобы извлечь JJ, иначе все после того, как "Ваше имя пользователя:"

Один из способов:

text = "hello john\nyour username is: jj\nthanks for signing up\n" 
match = text[/your username is: (.*)/] 
value = $1 

Но это напоминает мне о Perl .. и не «читает» так естественно, как мне сказали, рубин должен.

Есть ли более чистый способ? AKA «Рубиновый» способ?

Благодаря

+1

Ruby был на самом деле довольно сильно вдохновлен Perl; он должен был входить в ту же нишу, что и Perl, но с красивой системой объектов и синтаксисом, который был более чистым и более регулярным. На самом деле у него есть ряд функций, взятых прямо из Perl, таких как ruby ​​-p -i -e, хотя некоторые из более популярных функций Perl теперь устарели. –

ответ

22

Ваш код в значительной степени способ Руби. Если вы не хотите использовать глобальные $1, вы можете использовать 2 ARG версию String#[]:

match = text[/your username is: (.*)/, 1] 
+0

Спасибо. Это именно то, что я искал! Вытягивание долларовых глобалов просто показалось слишком старой школой. Пошел и прочитал документы API для Ruby, Class: String и там он был. http://www.ruby-doc.org/core/classes/String.html#M000786 – SWR

6

расколоть команда mindbogglingly полезна. Он делит строку на массив подстрок, разделяя все, что вы проходите. Если вы не дадите никаких аргументов, он разбивается на пробелы. Так что, если вы знаете, слово вы ищете является пятой «слово» (расщепление на обоих пространствах и обратный характер), вы можете сделать это:

текст = «Привет, Джон \ Nyour имя пользователя является: JJ \ nС уважением для подписания \ п»
матч = text.split [5]

..но, возможно, не достаточно самодокументирован, или вы хотите, чтобы для нескольких слов спичек. Вы могли бы сделать это вместо:

срединный = text.split ("\ п") [1]
матч = midline.split ("Имя пользователя является:") .last

Или, возможно, это более лаконичный способ:

матч = текст [/ имя пользователя является: (. *) /, 1]

+0

Я бы сделал это, но разделился на "" вместо "вашего имени пользователя:" –

+1

+1 для интересного использования раскола, чтобы получить пятое слово, я этого не заметил. –

+2

Вау, спасибо за несколько путей атаки.;) Я не заметил возможности разделения, но входящий текст не является статичным (пример был значительно упрощен), поэтому он не будет работать ... но это был хороший способ атаковать проблему. – SWR

4

Не уверен, если это больше Ruby'ish, но другой вариант:

>> text = "hello john\nyour username is: jj\nthanks for signing up\n" 
>> text.match(/your username is: (.*)/)[1] 
=> "jj" 
+2

Вот как я это сделаю. Это не технически превосходит решение [], но я думаю, что цель понятна, когда вы его снимаете. – Chuck

3

Там в также Regexp#match, который возвращает объект MatchData, который имеет всю необходимую информацию.

irb> match = /your username is: (.*)/.match "hello john\nyour username is: jj\nthanks for signing up\n" 
#=> #<MatchData:0x557f94> 
irb> match.pre_match 
#=> "hello john\n" 
irb> match.post_match 
#=> "\nthanks for signing up\n" 
irb> match[0] 
#=> "your username is: jj" 
irb> match[1] 
#=> "jj" 
Смежные вопросы