#ruby-on-rails
#ruby-on-rails
Вопрос:
Я создаю приложение, которое ограничивает количество слов, а не символов, в поле.
Как мне это сделать?
Комментарии:
1. Путем подсчета количества пробелов 1.
2. @mischa, строка типа
<space><space>hello<space><space>there<space><space>
возвращала бы ложное количество пробелов, если бы вы считали только пробелы.3. @Zabba: Хм, да, ты прав. Это была просто моя первая мысль.. Я очень плох в регулярных выражениях, но ваше решение должно быть лучше.
4. вы могли бы использовать string strip() и squeeze(» «), чтобы удалить лишние пробелы
Ответ №1:
По умолчанию Split разделяется на (белое) пространство, поэтому:
s.split.size
должен получить количество слов для вас.
Если вы хотите использовать это при проверке:
class Widget < ActiveRecord::Base
validate :word_count_is_less_than_5
private
def word_count_is_less_than_5
errors[:widget] << "too many words" if desc.split.size > 4
end
end
Комментарии:
1. Я подумал, что это может быть тем, о чем вы спрашивали. Пожалуйста, смотрите отредактированный ответ выше.
2. @seph, ice Я собираюсь опробовать это на следующий день… Я думаю, что это имеет смысл для меня …. но также сравнивая другой ответ выше, что вы думаете?
3. @Angela — Достаточно справедливо.
desc.scan(/S /).size
тоже должно сработать.4. @seph — небольшой вопрос. В вашем ответе указано «desc», предполагая, что атрибутом, который я хочу проверить в виджете, является desc (Widget.desc)? Я заметил, что другие проверки указывают атрибут в операторе validate?
5. @Angela — Да, desc — это атрибут, который вы хотите проверить. В модели виджет можно отключить. Понятно, что вы работаете с виджетом.
Ответ №2:
Используйте регулярное выражение для подсчета слов, а затем используйте его при проверке:
def word_count(s)
count = 0
s.scan(/bS b/) { count = count 1}
count
end
Ответ №3:
На самом деле есть очень простой способ сделать это благодаря :tokenizer
опции. Этот пример ограничивает поле summary в моей модели максимум 250 словами.
validates :summary, :presence => true, :length => {
:maximum => 250,
:tokenizer => lambda { |str| str.scan(/w /) },
:too_long => "Please limit your summary to %{count} words"
}
В этом случае токенизатор разбивает строку на слова.