O que string :: npos significa neste código?


91

O que a frase std::string::npossignifica no seguinte trecho de código?

found = str.find(str2);

if (found != std::string::npos)
    std::cout << "first 'needle' found at: " << int(found) << std::endl;

Respostas:


105

Isso significa que não foi encontrado.

Geralmente é definido assim:

static const size_t npos = -1;

É melhor comparar com npos em vez de -1 porque o código é mais legível.


3
Comparar == -1 também pode fazer algumas pessoas pensarem que podem converter isso em <0 que NÃO é a mesma coisa e não funcionará.
Andy Dent,

Só estou me perguntando se alguém já passou por isso, ou sou só eu ... Eu corro cout<<"pos: "<<str.find("not in the string")<<" npos: "<<std::string::npos;e consigo pos:4294967295 npos: 4294967295quando executo no Windows, mas no Mac eu consigo pos:4294967295 npos: 18446744073709551615. Isso não parece certo ... bem, de qualquer forma, sugiro comparar com, em -1vez destd::string::npos
user1135469

@ user1135469 se você vir a resposta do codaddict abaixo ( stackoverflow.com/a/3827997/752842 ) ou de Sebastian Raschka, acho que o que você está recebendo fará sentido. E eu recomendaria usar npos, porque tentei usar -1 e não estava funcionando corretamente nas condições em que estava usando.
Dzyann

51

string::nposé uma constante (provavelmente -1) que representa uma não posição. Ele é retornado pelo método findquando o padrão não foi encontrado.


15
+1 para realmente mostrar a derivação npos = no-pos que torna mais fácil de lembrar. É tão óbvio que você não pensaria nisso depois de sabê-lo, mas para alguém que vê essas letras pela primeira vez, pode não clicar ...?
Tony Delroy

4
errado em 47 níveis ... npos é de size_t, isso significa que não pode ser negativo ... o significado real é max_index, 18446744073709551615 para 64 bits size_t
NoSenseEtAl

25

O documento para string::nposdiz:

npos é um valor constante de membro estático com o maior valor possível para um elemento do tipo size_t.

Como valor de retorno, geralmente é usado para indicar falha.

Esta constante é realmente definida com um valor de -1 (para qualquer característica), que porque size_t é um tipo integral sem sinal, torna-se o maior valor representável possível para este tipo.


17

size_té uma variável sem sinal, portanto, 'valor sem sinal = - 1' a torna automaticamente o maior valor possível para size_t: 18446744073709551615


size_t é int sem sinal para compilador de 32 bits; unsigned long long int para compilador de 64 bits. Definindo-o como -1, ele terá o valor máximo daquele tipo unsigned.
sudheerbb

9

std::string::nposé o índice definido pela implementação que está sempre fora dos limites de qualquer std::stringinstância. Várias std::stringfunções o retornam ou aceitam para sinalizar além do fim da situação da string. Geralmente é de algum tipo inteiro sem sinal e seu valor geralmente std::numeric_limits<std::string::size_type>::max ()é (graças às promoções de inteiro padrão) geralmente comparável a -1.


4

temos que usar string::size_typepara o tipo de retorno da função find, caso contrário, a comparação com string::npospode não funcionar. size_type, que é definido pelo alocador da string, deve ser um unsigned tipo integral. O alocador padrão, alocador, usa o tipo size_tcomo size_type. Como -1é convertido em um tipo integral sem sinal, npos é o valor máximo sem sinal de seu tipo. No entanto, o valor exato depende da definição exata do tipo size_type. Infelizmente, esses valores máximos são diferentes. Na verdade, (unsigned long)-1difere de (unsigned short)-1 se o tamanho dos tipos for diferente. Assim, a comparação

idx == std::string::npos

pode resultar em falso se idx tiver o valor -1e idx e string::npostiver tipos diferentes:

std::string s;
...
int idx = s.find("not found"); // assume it returns npos
if (idx == std::string::npos) { // ERROR: comparison might not work
...
}

Uma maneira de evitar esse erro é verificar se a pesquisa falha diretamente:

if (s.find("hi") == std::string::npos) {
...
}

No entanto, geralmente você precisa do índice da posição do caractere correspondente. Assim, outra solução simples é definir seu próprio valor assinado para npos:

const int NPOS = -1;

Agora a comparação parece um pouco diferente e ainda mais conveniente:

if (idx == NPOS) { // works almost always
...
}

3

foundserá nposno caso de falha em encontrar a substring na string de pesquisa.


1
$21.4 - "static const size_type npos = -1;"

Ele é retornado por funções de string indicando erro / não encontrado etc.


0

npos é apenas um valor de token que informa que find () não encontrou nada (provavelmente -1 ou algo parecido). find () verifica a primeira ocorrência do parâmetro e retorna o índice no qual o parâmetro começa. Por exemplo,

  string name = "asad.txt";
  int i = name.find(".txt");
  //i holds the value 4 now, that's the index at which ".txt" starts
  if (i==string::npos) //if ".txt" was NOT found - in this case it was, so  this condition is false
    name.append(".txt");

Este código não wort para "asad.other" porque find () não retorna um int.
LogicMagic de

0

const estático size_t npos = -1;

Valor máximo para size_t

npos é um valor constante de membro estático com o maior valor possível para um elemento do tipo size_t.

Este valor, quando usado como o valor para um parâmetro len (ou sublen) em funções de membro de string, significa "até o final da string".

Como um valor de retorno, geralmente é usado para indicar nenhuma correspondência.

Essa constante é definida com um valor de -1, que como size_t é um tipo integral sem sinal, é o maior valor representável possível para esse tipo.


0

Uma resposta para os dias de C ++ 17, quando temos std::optional:

Se você apertar os olhos um pouco e fingir que std::string::find()retorna um std::optional<std::string::size_type>(o que deveria ...) - então a condição se torna:

auto position = str.find(str2);

if ( position.has_value() ) {
    std::cout << "first 'needle' found at: " << found.value() << std::endl;
}

0

O valor de string :: npos é 18446744073709551615. É um valor retornado se nenhuma string for encontrada.


O valor real é definido pela implementação e irrelevante. Na prática, no entanto, o valor 18446744073709551615seria típico para 64 bits std::size_t, é o valor máximo sem sinal de 64 bits.
Alex Guteniev
Ao utilizar nosso site, você reconhece que leu e compreendeu nossa Política de Cookies e nossa Política de Privacidade.
Licensed under cc by-sa 3.0 with attribution required.