Отловить цифры перед заданным текстом в jQuery

344
07 марта 2017, 16:14

Для динамической смены курса валюты на страницы пытаюсь отловить все цифры перед текстом 'рубль':

var curnums = $('body').text().match('^\D*(\d+) рублей.*$');

но в ответ тишина. Честно говоря, не совсем силен в регулярке.

Ну и в довесок - каким образом можно процесс отлавливания загнать в цикл, чтобы менять значение на нужное при нахождении подстроки?

Answer 1

В JavaScriptʼе '^\D*(\d+) рублей.*$' — это строка, а не регулярное выражение. Регулярные выражения заключаются в символы /.../. '...' — это строка, а не регулярное выражение, то есть в Вашем коде производится поиск строки '^\D*(\d+) рублей.*$'.

Дальше. Ваше регулярное выражение начинается с символа начала строки (^) и заканчивается символом конца строки ($). То есть сравнивается обязательно вся строка. Если Вы не проверяете всю строку на корректность, а ищите что-то внутри строки, не используйте ^ и $, они лишние.

Плюс уберите «что угодно» (.*) в конце, ведь в таком случае регулярное выражение захватит всё, что осталось, до конца — включая следующие числовые даты, а нам это не нужно.

Получаем такое регулярное выражение: /(\d+) рублей/

В принципе, после цифры может быть не только пробел, а и, например, табуляция. Так что лучше заменить на \s. Причём пробельных символов может быть несколько, так что лучше поставить + (\s+).

Возможно, имеет смысл не только «рублей», но и «рубля», и «рубль», и «руб.», так что лучше сделать так: /(\d+)\s+руб(лей|ля|ль|\.)/

Правда, это не включает копейки. Предположим, что копейки идут сразу после рублей (вообще-то это не обязательно верно — смотрите свои входные данные, но предположим). Также предположим, что копейки без рублей не встречаются:

/(\d+)\s+руб(лей|ля|ль|\.)(\s*(\d+)\s+коп(еек|йки|йка|\.))?/

Я обвёл копейки в скобки и поставил ? после скобок, чтобы указать, что что копейки указывать не обязательно.

Чтобы заменить все значения, можно использовать функцию replace, передав ей функцию — примерно вот так:

исходнаяСторока.replace(/регулярка/g, function (match, скобки1, скобки2, скобки3, ...) {
  return 'чем заменить';
});

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

Для примера, вот функция, которая переводит рубли в доллары:

function rublesToDollars(str, course) {
  return str.replace(
    /(\d+)\s+руб(лей|ля|ль|\.)(\s*(\d+)\s+коп(еек|йки|йка|\.))?/g,
    function (match, rubles, rub_ending, copecks_match, copecks, copecks_ending) {
      var rubles = parseInt(rubles);
      if (copecks) {
        rubles += parseInt(copecks) / 100;
      }
      var dollars = rubles / course;
      return dollars.toFixed(2) + '$';
    });
}

Вот пример использования:

rublesToDollars("Инна заказала пиццу Tut.by " +
    "за 8 рублей 90 копеек, а я — салат за 5 рублей " +
    "50 копеек", 1.9031)

Результат:

"Инна заказала пиццу Tut.by за 4.68$, а я — салат за 2.89$"

Дальше нужно применить это ко всему тексту. $("body").text() точно не подходит, так как это преобразование с потерей данных: вы теряете все теги внутри <body>, вы по сути делаете из HTMLʼа неформатированный текст.

Функция выше может работать только с текстом, но не с тегами. Если вы знаете, что текст с суммами будет храниться только в определённых элементах (например, в описаниях товаров), то проще всего заменить текст только в этих элементах.

Если Вам нужно что-то более универсальное, то лучше воспользоваться готовыми плагинами для замены во всём коде. Например, https://github.com/padolsey/findAndReplaceDOMText

READ ALSO
onscroll при отсутствии сколла

onscroll при отсутствии сколла

Есть такой код, который говорит, что при скроллинге скролл достигнул конца страницы

298
Как работает функция click в jquery?

Как работает функция click в jquery?

Вот например, что делает вот эта?

314