J'essaie de trouver s'il y a une meilleure façon de vérifier si la chaîne a des caractères spéciaux. Dans mon cas, autre chose que l'alphanumérique et un '_' est considéré comme un caractère spécial. Actuellement, j'ai une chaîne contenant des caractères spéciaux tels que STD :: String = "! @ # $% ^ &". J'utilise ensuite l'algorithme STD :: Find_First_of () pour vérifier si l'un des caractères spéciaux est présent dans la chaîne. P>
Je me demandais comment le faire en fonction de la liste de bain. Je souhaite spécifier les caractères minuscules / majuscules, les numéros et un soulignement dans une chaîne (je ne veux pas les énumérer. Y a-t-il une façon de spécifier la gamme ASCII de quelque sorte comme [A-ZA-Z0-9_] ). Comment puis-je atteindre cet objectif? Ensuite, je prévois d'utiliser le std :: Find_First_not_of (). De cette façon, je peux mentionner ce que je veux réellement et vérifier le contraire. P>
9 Réponses :
Essayez: ou essayez de booster les expressions régulières: p>
Je sais que je peux le faire, mais je me demandais que je pourrais mentionner la gamme, telle que la plage de valeurs [A-Z A-Z 0-9 _] ou ASCII ou quelque chose.
@Praveen: version de boost ajoutée.
Regex va beaucoup plus simple depuis le poste: #include
Les fonctions (macros) sont soumises aux paramètres de paramètres régionaux, mais vous devriez étudier iSalnum () code> et des parents de
J'utiliserais simplement l'installation C intégrée ici. Itérate sur chaque caractère de la chaîne et vérifiez s'il est _ code> ou si
isalpha (ch) code> est vrai. Si oui, alors c'est valide, sinon c'est un caractère spécial. P>
Il n'y a aucun moyen d'utiliser Standard C ou C ++ pour le faire à l'aide de plages de caractères, vous devez répertorier tous les caractères. Pour C Strings, vous pouvez utiliser strSpn (3) code>
et strcspn (3) code>
pour trouver le premier caractère d'une chaîne C'est un membre ou n'est pas membre d'un jeu de caractères donné. Par exemple:
// Test if the given string has anything not in A-Za-z0-9_ bool HasSpecialCharacters(const char *str) { return str[strspn(str, "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789_")] != 0; }
La première chose à considérer est "Est-ce que ceci est seulement"? Si vous répondez est oui, je vous encourage-vous à déterminer vraiment si vous devez ou non laisser ASCII uniquement. Je travaille actuellement pour une entreprise qui a vraiment des maux de tête dans les marchés étrangers, car nous n'avions pas pensé à soutenir Unicode à partir de la gobing. P>
Cela étant dit, ASCII rend vraiment facile à vérifier pour les numériques non alpha. Jetez un coup d'œil au tableau ASCII. P>
http://fr.wikipedia.org/wiki/ascii#ascii_printable_characters < / p>
Si vous le souhaitez, mais ne voulez pas aller à l'ensemble du porc et utilisez REGEXPS, et étant donné que vous êtes testé, c'est pour les caractères ASCII - Créez simplement une fonction pour générer la chaîne pour Find_First_not_of code> ...
#include <iostream>
#include <string>
std::string expand(const char* p)
{
std::string result;
while (*p)
if (p[1] == '-' && p[2])
{
for (int c = p[0]; c <= p[2]; ++c)
result += (char)c;
p += 3;
}
else
result += *p++;
return result;
}
int main()
{
std::cout << expand("A-Za-z0-9_") << '\n';
}
Je pense que je ferais le travail juste un peu différemment, traiter le au moins lorsque vous traitez avec Si vous voulez faire le travail avec pure C, vous pouvez utiliser std :: string code> en tant que collection et en utilisant un algorithme. Utilisation d'un C ++ 0x Lambda, il ressemblerait à quelque chose comme ceci:
char code> (pas
wchar_t code>),
isalnum code> utilisera généralement une table lève-t-il, il sera donc généralement plus rapide que n'importe quoi basé sur
Find_first_of code> (qui utilisera normalement un recherche linéaire à la place). Iow, c'est O (n) (n = str.size ()), où quelque chose basé sur
wind_first_of code> sera O (n * m), (n = str.size (), m = motif.size ()). p>
scanef code> avec une conversion de scanset théoriquement non portable, mais supportée par essentiellement Tous les compilateurs récents / populaires: P>
char junk;
if (sscanf(str, "%*[A-Za-z0-9_]%c", &junk))
/* it has at least one "special" character
else
/* no special characters */
Isalnum code> est optimisé, il ne fait pas une liste de tables, mais elle vérifie si le caractère est dans une plage: le code fonctionne comme
('0' <= '= C && C <=' 9 ') || ('A' <= c && c <= 'z') || ('a' <= c && c <= 'z') code> où c est le caractère. Il utilise le fait que les caractères (d'un groupe comme des lettres ou des chiffres supérieurs ou inférieurs) sont linéaires après l'autre en ASCII. Ceci est plus efficace que la regex (qui nécessite un analyseur ou un interpréteur) ou Find_First_not_of.
@CMDLP: Il appartient à la mise en œuvre de décider comment la mettre en œuvre, bien sûr. Cela dit, ici (pour un exemple) est de savoir comment il est mis en œuvre dans LIBSTDC ++ pour Linux: Retour _M_TABLE [STATIC_CAST
retour isasciii (c)? (CTYPE
@CMDLP: Si vous en connaissez un lieu où il est basé sur la comparaison avec les gammes, je serais intéressé à savoir ce que c'est - je crois à l'heure actuelle, qui est de bonne chance d'être plus efficace qu'une table Recherche, mais je ne connais aucune mise en œuvre qui le fait réellement.
Utiliser
s.erase(std::remove_if(s.begin(), s.end(), my_predicate), s.end()); bool my_predicate(char c) { return !(isalpha(c) || c=='_'); }
Vous pouvez utiliser quelque chose comme ceci:
#include <ctype> for(int i=0;i<s.length();i++){ if( !std::isalpha(s[i]) && !std::isdigit(s[i]) && s[i]!='_') return false }
Stackoverflow.com/q/1120198/82705
@Sai Ganesh: langue différente là-bas (C #)
C ++ n'assume pas ASCII. Il est même compatible avec EBCDIC, dans lequel A-Z n'est pas contiguë.