Что возвращает find c
Перейти к содержимому

Что возвращает find c

  • автор:

Что возвращает find c

Функция find() возвращает индекс первого вхождения подстроки или отдельного символа в строке в виде значние я типа size_t :

#include #include int main() < std::string text ; std::cout 

Если строка или символ не найдены (как в примере выше в последнем случае), то возвращается специальная константа std::string::npos , которая представляет очень большое число (как видно из примера, число 18446744073709551615). И при поиске мы можем проверять результат функции find() на равенство этой константе:

if (text.find("banana") == std::string::npos)

Функция find имеет ряд дополнительных версий. Так, с помощью второго параметра мы можем указать индекс, с которого надо вести поиск:

#include #include int main() < std::string text ; // поиск с 10-го индекса std::cout 

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

#include #include int main() < std::string text ; std::string word ; unsigned count<>; // количество вхождений for (unsigned i <>; i std::cout 

Здесь в цикле пробегаемся по тексту, в котором надо найти строку, пока счетчик i не будет равен text.length() - word.length() . С помощью функции find() получаем индекс первого вхождения слова в тексте, начиная с индекса i. Если таких вхождений не найдено, то выходим из цикла. Если же найден индекс, то счетчик i получает индекс, следующий за индексом найденного вхождения.

В итоге, поскольку искомое слово "friend" встречается в тексте два раза, то программа выведет

The word is found 2 times.

В качестве альтернативы мы могли бы использовать цикл while :

#include #include int main() < std::string text ; std::string word ; unsigned count<>; // количество вхождений size_t index<>; // начальный индекс while ((index = text.find(word, index)) != std::string::npos) < ++count; index += word.length(); // перемещаем индекс на позицию после завершения слова в тексте >std::cout

Еще одна версия позволяет искать в тексте не всю строку, а только ее часть. Для этого в качестве третьего параметра передается количество символов из искомой строки, которые программа будет искать в тексте:

#include #include int main() < std::string text ; std::string word ; // поиск с 10-го индекса 3 первых символов слова "endless", то есть "end" std::cout 

Стоит отметить, что в этом случае искомая строка должна представлять строковый литерал или строку в С-стиле (например, символьный массив с концевым нулевым байтом).

Функция rfind. Поиск в обратном порядке

Функция rfind() работает аналогично функции find() , принимает те же самые параметры, только ищет подстроку в обратном порядке - с конца строки:

#include #include int main() < std::string text ; std::cout 

Поиск любого из набора символов

Пара функций - find_first_of() и find_last_of() позволяют найти соответственно первый и последний индекс любого из набора символов:

#include #include int main() < std::string text ; std::string letters; // искомые символы std::cout 

В данном случае ищем в строке "Phone number: +23415678901" первую и последнюю позицию любого из символов из строки "0123456789". То есть таким образом мы найдем начальный и конечный индекс номера телефона.

Если нам, наоборот, надо найти позиции символов, которые НЕ представляют любой символ из набора, то мы можем использовать функции find_first_not_of() (первая позиция) и find_last_not_of() (последняя позиция):

#include #include int main() < std::string text ; std::string letters; // искомые символы std::cout 

Мы можем комбинировать функции. Например, найдем количество слов в строке:

#include #include int main() < std::string text ; // исходный текст const std::string separators< " ,;:.\"!?'*\n" >; // разделители слов unsigned count<>; // счетчик слов size_t start < text.find_first_not_of(separators) >; // начальный индекс первого слова while (start != std::string::npos) // если нашли слово < // увеличиваем счетчик слов count++; size_t end = text.find_first_of(separators, start + 1); // находим, где кончается слово if (end == std::string::npos) < end = text.length(); >start = text.find_first_not_of(separators, end + 1); // находим начальный индекс следующего слова и переустанавливаем start > // выводим количество слов std::cout 

Вкратце рассмотрим данный код. В качестве текста, где будем подсчитывать слова, определям переменную text. И также определяем строку разделителей, такие как знаки пунктуации, пробелы, символ перевода строки, которые не являются словами:

const std::string separators< " ,;:.\"!?'*\n" >; // разделители слов

Перед обработкой введенного текста фиксируем индекс первого символа первого слова в тексте. Для этого применяется функция find_first_not_of() , которая возвращает первый индекс любого символа, который не входит в строку separators:

size_t start < text.find_first_not_of(separators) >;

Далее в цикле while смотрим, является ли полученный индекс действительным индексом:

while (start != std::string::npos)

Например, если в строке одни только символы из набора separators, тогда функция find_first_not_of() возвратит значение std::string::npos , что будет означать, что в тексте больше нет непунктационных знаков.

И если start указывает на действительный индекс начала слова, то увеличиваем счетчик слово. Далее находим индекс первого символа из separators, который идет сразу после слова. То есть фактически это индекс после последнего символа слова, который помещаем в переменную end:

size_t end = text.find_first_of(separators, start + 1); // находим, где закончилось слово

Для нахождения позиции окончания слова используем функцию find_first_of() , которая возвращает первую позицию любого символа из separators, начиная с индекса start+1

Причем может быть, что функция find_first_of() не найдет ни одного символа из separators (например, слово является поседним в тексте, и после него нет никаких знаков пунктуации или пробелов), в этом случае конечный индекс равен длине текста.

if (end == std::string::npos) // если НЕ найден ни один из символов-разделителей end = text.length(); // устанавливаем переменную end на конец текста

После того, как мы нашли начальный индексы слова и его конец, переустанавливаем start на начальный индекс следующего слова и повторяем действия цикла:

start = text.find_first_not_of(separators, end + 1); // находим начальный индекс следующего слова и переустанавливаем start

В конце выводим количество найденных слов.

Команда FIND - поиск строки символов в файле

Команда FIND используется для поиска текстовой строки в одном или нескольких файлах. Если путь не задан, команда FIND выполняет поиск в тексте консоли либо в тексте, переданном по конвейеру другой командой ( в тексте, являющемся выводом команды, выполняющейся в цепочке с FIND ).

Формат командной строки:

FIND [/V] [/C] [/N] [/I] [/OFF[LINE]] "строка" [[диск:][путь]имя_файла[ . ]] Параметры команды:

/V - Вывод всех строк, НЕ содержащих заданную строку.
/C - Вывод только общего числа строк, содержащих заданную строку.
/N - Вывод номеров отображаемых строк.
/OFF[LINE] - Не пропускать файлы с установленным атрибутом "Автономный".
/I - Поиск без учета регистра символов.
"строка" - Искомая строка.
[диск:][путь]имя_файла - Один или несколько файлов, в которых выполняется поиск.

FIND /? - выдать справку по использованию команды.

find /I myfile.txt "новость" - выполнить поиск строки новость без учета регистра символов в текстовом файле myfile.txt . По умолчанию, если не задан параметр /I регистр символов учитывается.

find /C myfile.txt "новость" - отобразить общее количество строк, содержащих текст "новость".

FIND /I %TEMP%\*.tmp "windows" - выполнить поиск в каталоге временных файлов для всех файлов с расширением tmp строк , содержащих текст windows без учета регистра символов.

FIND /I %TEMP%\*.tmp "windows" | more - то же, что и в предыдущем примере, но с использованием постраничного вывода на экран.

ipconfig /all | FIND "DNS" - из вывода команды ipconfig /all найти строки, содержащие текст DNS

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

Соответственно, пример с поиском во временных файлах, приведенный выше, в ОС Windows XP ( значение переменной %TEMP% по умолчанию принимает путь с пробелами ) будет выполняться верно при использовании следующей команды:

Естественно, шаблон имени файла *.tmp использовавшийся в примере выше, при перенаправлении ввода применять нельзя ( перенаправление можно выполнять для конкретного файла - textfile.tmp в примере ) и для организации поиска текстовой строки в нескольких файлах можно воспользоваться циклической обработкой их содержимого , например, с помощью команды FOR .

@ECHO OFF
for %%i in ("%TEMP%\*.tmp") do FIND %%i "windows"
. . .

Применение команды FIND для поиска строки в результатах вывода другой программы используется, например, для определения доступности сетевого узла с помощью команды PING . Утилита ping.exe не возвращает признак доступности пингуемого адреса в значении переменной ERRORLEVEL (Ненулевое значение ERRORLEVEL утилита ping.exe формирует только в том случае, если заданы ошибочные параметры командной строки). Поэтому, для определения доступности IP- адреса, используется анализ вывода ping.exe, который отличается для доступного и недоступного узла. Так, например, если пингуемый адрес доступен, то в сообщении будет присутствовать значение TTL :

Обмен пакетами с yandex.ru [87.250.250.11] по 32 байт:
Ответ от 87.250.250.11: число байт=32 время=10мс TTL=55

А в случае недоступности, строка символов "TTL" в выводимых результатах отсутствует. Если строка символов "TTL" найдена, то FIND сформирует значение переменной ERRORLEVEL равным 0 Таким образом, для определения факта доступности узла в командном файле можно воспользоваться следующим способом:

ping -n 1 COMPUTER | find /I "TTL" > nul
if %ERRORLEVEL%==0 goto LIVE
ECHO computer не доступен
подпрограмма обработки недоступного состояния
. . .
Exit
:LIVE - начало подпрограммы обработки состояния доступности узла
. . .
. . .

Команда ping используется в цепочке с командой find (конвейер ) и результаты ее вывода используются в качестве ввода для поиска строки " TTL ". В конвейер добавлена команда перенаправления стандартного вывода на фиктивное устройство nul, т.е. подавление вывода. Ключ -n 1 задает однократный опрос узла COMPUTER для ping.exe.

Array.prototype.find()

Метод find() возвращает значение первого найденного в массиве элемента, которое удовлетворяет условию переданному в callback функции. В противном случае возвращается undefined .

Также смотрите метод findIndex() , который возвращает индекс найденного в массиве элемента вместо его значения.

Если вам нужно найти позицию элемента или наличие элемента в массиве, используйте Array.prototype.indexOf() или Array.prototype.includes() соответственно.

Синтаксис

arr.find(callback[, thisArg])

Параметры

Функция, вызывающаяся для каждого значения в массиве, принимает три аргумента:

Текущий обрабатываемый элемент в массиве.

Индекс текущего обрабатываемого элемента в массиве.

Массив, по которому осуществляется проход.

Необязательный параметр. Значение, используемое в качестве this при выполнении функции callback .

Возвращаемое значение

Значение элемента из массива, если элемент прошёл проверку, иначе undefined .

Описание

Метод find вызывает переданную функцию callback один раз для каждого элемента, присутствующего в массиве, до тех пор, пока она не вернёт true . Если такой элемент найден, метод find немедленно вернёт значение этого элемента. В противном случае, метод find вернёт undefined . До Firefox 34 функция callback не вызывалась для «дырок» в массивах (bug 1058394).

Функция callback вызывается с тремя аргументами: значением элемента, индексом элемента и массивом, по которому осуществляется проход.

Если в метод find был передан параметр thisArg , при вызове callback он будет использоваться в качестве значения this . В противном случае в качестве значения this будет использоваться значение undefined .

Метод find не изменяет массив, для которого он был вызван.

Диапазон элементов, обрабатываемых методом find , устанавливается до первого вызова функции callback . Элементы, добавленные в массив после начала выполнения метода find , не будут посещены функцией callback . Если существующие, непосещение элементы массива изменяются функцией callback , их значения, переданные в функцию, будут значениями на тот момент времени когда метод find посетит их; удалённые элементы все ещё будут посещены.

Примеры

Пример: поиск простого числа в массиве

Следующий пример находит в массиве положительных чисел элемент, являющийся простым числом (либо возвращает undefined , если в массиве нет простых чисел).

function isPrime(element, index, array)  var start = 2; while (start  Math.sqrt(element))  if (element % start++  1)  return false; > > return element > 1; > console.log([4, 6, 8, 12].find(isPrime)); // undefined, не найдено console.log([4, 5, 8, 12].find(isPrime)); // 5 

Полифил

Этот метод был добавлен в спецификации ECMAScript 6 и пока может быть недоступен во всех реализациях JavaScript. Однако, вы можете использовать следующий сниппет в качестве полифила:

// https://tc39.github.io/ecma262/#sec-array.prototype.find if (!Array.prototype.find) < Object.defineProperty(Array.prototype, 'find', < value: function(predicate) < // 1. Let O be ? ToObject(this value). if (this == null) < throw new TypeError('"this" is null or not defined'); >var o = Object(this); // 2. Let len be ? ToLength(? Get(O, "length")). var len = o.length >>> 0; // 3. If IsCallable(predicate) is false, throw a TypeError exception. if (typeof predicate !== 'function') < throw new TypeError('predicate must be a function'); >// 4. If thisArg was supplied, let T be thisArg; else let T be undefined. var thisArg = arguments[1]; // 5. Let k be 0. var k = 0; // 6. Repeat, while k < len while (k < len) < // a. Let Pk be ! ToString(k). // b. Let kValue be ? Get(O, Pk). // c. Let testResult be ToBoolean(? Call(predicate, T, « kValue, k, O »)). // d. If testResult is true, return kValue. var kValue = o[k]; if (predicate.call(thisArg, kValue, k, o)) < return kValue; >// e. Increase k by 1. k++; > // 7. Return undefined. return undefined; >, configurable: true, writable: true >); >

Спецификации

Specification
ECMAScript Language Specification
# sec-array.prototype.find

Совместимость с браузерами

BCD tables only load in the browser

Смотрите также

  • Array.prototype.findIndex() Экспериментальная возможность
  • Array.prototype.every()

Found a content problem with this page?

  • Edit the page on GitHub.
  • Report the content issue.
  • View the source on GitHub.

This page was last modified on 4 авг. 2023 г. by MDN contributors.

Your blueprint for a better internet.

Почему std::find возвращает указатель?

зачем использовать именно указатель p, а не просто переменную p. Мы же не собираемся никак менять элемент массива. Нам просто нужно поискать его в массиве и все. Почему нельзя это сделать без указателя? Заранее спасибо!

Отслеживать
122k 24 24 золотых знака 124 124 серебряных знака 297 297 бронзовых знаков
задан 10 янв 2021 в 23:15
331 4 4 серебряных знака 15 15 бронзовых знаков

std::find ищет в диапазоне [first, last) ( last не включается) возвращает last , если ничего не найдено

10 янв 2021 в 23:51

3 ответа 3

Сортировка: Сброс на вариант по умолчанию

  1. То, что ты в конкретном примере чего-то делать не собираешься, не означает, что это не нужно. То, что возвращает find может использоваться и для изменения значения, и даже для изменения контейнера - например, обрезать вектор после или перед найденным элементом. А ещё можно что-то делать с соседними элементами.
  2. Даже если представить, что по некоторой причине завелись две функции - одна ищет указатель (а вообще-то она шаблонная и указатель - это твой вариант, а там может быть любой итератор), а другая - значение, то со значением возникает проблема. Надо как-то уметь отличать ситуацию, когда значение найдено от ситуации, когда оно не найдено. Поскольку мы можем искать любое значение, то надо каким-то образом обеспечить возможность возврата на одно значение больше, чем вмещает используемый тип. Например, при считывании файла нормальные символы вмещаются в char, а getc возвращает int чтобы суметь предоставить EOF вне допустимого диапазона char. Очевидно, что для произвольного типа это сделать затруднительно и чуть ли не единственным вариантом станет возвращать структуру с найденным значением и флагом. Стоп. Структуру с найденным значением? Но не копировать же в неё значение? Тогда структуру с указателем и флагом? А нафига нам теперь флаг, если сам указатель можно использовать для того, чтобы показать, что ничего не найдено?
  3. Ну и конкретно про find. Ты ему передаёшь число 30. Если представить, что он вернёт тебе те же самые 30, то нафига тебе это надо? Функция, которая принимает пару итераторов и возвращает свой третий аргумент?
  4. А в твоём коде можно заменить find на count, тогда число можно сразу использовать в качестве флага. Впрочем, формально производительность этого кода будет хуже, если только компилятор не догадается что-нибудь заинлайнить и выкинуть лишнее, так что я бы оставил find.

Отслеживать
ответ дан 11 янв 2021 в 0:09
122k 24 24 золотых знака 124 124 серебряных знака 297 297 бронзовых знаков

Есть еще std::any_of , который вернет истину, если хотя бы для одного элемента предикат вернет true .

11 янв 2021 в 6:53
@Croessmah, но ему нужен предикат, то в данном случае менее удобно.
11 янв 2021 в 7:15

Здравствуйте! А почему после просьбы "найдите в толпе человека с красной шапкой" вы пальцем указываете на этого человека, а не отвечаете "человек с красной шапочкой".

Принимает любой тип, который ведет себя как указатель ( итератор для чтения ) и возвращает его(в данном случаи указатель). Это обобщенный алгоритм, и для него логична команда "отсюда до сюда найти это". Алгоритм находит и "говорит", что нашел его в этом месте (возвращает итератор, указывающий на это место) или не нашел(возвращает итератор, указывающий за конец последовательности.

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

Добавить комментарий

Ваш адрес email не будет опубликован. Обязательные поля помечены *