Comment vérifier qu'une chaîne Java n'est pas composée de tous les espaces?

132

Je veux vérifier que Java String ou tableau de caractères n'est pas uniquement composé d'espaces, en utilisant Java?

C'est une question très similaire sauf que c'est Javascript:
Comment puis-je vérifier si la chaîne contient des caractères et des espaces, pas seulement des espaces?

EDIT : J'ai supprimé le mot sur les caractères alphanumériques, donc cela a plus de sens.

Ankur
la source
3
Sachez qu'il existe de nombreuses définitions différentes de l'espace blanc: spreadsheets.google.com/pub?key=pd8dAQyHbdewRsnE5x5GzKQ Que voulez-vous? Ou alors vous dites "a un caractère alphanumérique", ce qui est une chose complètement différente. Précisez s'il vous plaît.
Kevin Bourrillion
Toutes mes excuses pour la confusion ... tous les espaces ne sont pas la clé - fondamentalement, si elle contient tous les caractères d'espacement, je veux l'exclure, car elle n'a pas de contenu.
Ankur
1
Avec JDK / 11, vous pouvez utiliser l'String.isBlank API pour la même chose.
Naman

Réponses:

224

La solution la plus courte à laquelle je puisse penser:

if (string.trim().length() > 0) ...

Cela vérifie uniquement les espaces (non) blancs. Si vous voulez vérifier des classes de caractères particulières, vous devez utiliser le mighty match()avec une expression rationnelle telle que:

if (string.matches(".*\\w.*")) ...

... qui vérifie au moins un caractère alphanumérique (ASCII).

Carl Smotricz
la source
9
FWIW: Je m'attendrais à ce que la première solution soit considérablement plus rapide.
Stephen C
2
@Stephen C: Absolument! Mais comme @Uri l'a souligné, je dois résoudre deux problèmes différents grâce à l'ambiguïté de la question :) Aussi, j'utilise rarement matches(): pour la performance, je stocke généralement le Patterndans un fichier final static. Paye si le même code s'exécute fréquemment.
Carl Smotricz
3
@Andreas_D: Heh, j'ai mes commandes! L'OP a dit qu'il voulait vérifier une chaîne ou un tableau de caractères, il n'a jamais rien dit à propos des valeurs nulles! :) * vérifie les petits caractères dans le contrat * " nulln'est pas une chaîne!"
Carl Smotricz
1
En outre, "\\ w" correspond uniquement à un sous-ensemble limité de caractères non blancs plutôt qu'à tous les caractères non blancs, car il fait référence à des "caractères de mot" définis comme AZ, az, 0-9 et trait de soulignement.
Rob Raisch
2
J'ai utilisé your_string.trim (). IsEmpty () et j'ai fait le travail pour moi
Neri
59

J'utiliserais la bibliothèque Apache Commons Lang. Il a une classe appelée StringUtils qui est utile pour toutes sortes d'opérations String. Pour vérifier si une chaîne n'est pas composée de tous les espaces, vous pouvez utiliser ce qui suit:

StringUtils.isBlank(<your string>)

Voici la référence: StringUtils.isBlank

Chris J
la source
8
Je préfère cette solution par rapport à l'utilisation de la réponse choisie. Cela vérifiera également la chaîne == null
Richard
C'est maintenant incorrect. StringUtils.isEmptyretournera désormais false si vous passez "".
James Spence
53

Légèrement plus court que ce qui a été mentionné par Carl Smotricz:

!string.trim().isEmpty();
chaux rouge
la source
10
Vous les jeunes whippersnappers et votre nouvelle supercherie post-Java-1.6! Sérieusement, au moins un projet dans mon entreprise fonctionne toujours sur Java 1.4 (soupir).
Carl Smotricz
Plus court? Oui. Personnellement, j'aime le style de codage plus verbeux
Michel
9

Si vous utilisez Java 11 , la nouvelle isBlankméthode de chaîne vous sera utile:

!s.isBlank();

Si vous utilisez Java 8, 9 ou 10 , vous pouvez créer un flux simple pour vérifier qu'une chaîne n'est pas uniquement un espace:

!s.chars().allMatch(Character::isWhitespace));

En plus de ne nécessiter aucune bibliothèque tierce telle qu'Apache Commons Lang, ces solutions ont l'avantage de gérer n'importe quel caractère d'espace blanc, et pas seulement des ' 'espaces simples comme le ferait une trimsolution basée sur une solution suggérée dans de nombreuses autres réponses. Vous pouvez vous référer aux Javadocs pour une liste exhaustive de tous les types d'espaces blancs pris en charge. Notez que les chaînes vides sont également couvertes dans les deux cas.

Pyves
la source
5
if(target.matches("\\S")) 
    // then string contains at least one non-whitespace character

Notez l'utilisation de la barre oblique inversée cap-S, qui signifie "caractère non-blanc"

Je parierais que c'est la solution la plus simple (et peut-être la plus rapide?).

Rob Raisch
la source
2
Essayons: String year="1995"; year.matches("\\S"); will return falsece n'est donc pas la bonne solution. : |
Nhat Dinh
6
Nhat, vous avez raison, même si je ne sais pas pourquoi. Selon la documentation Java, String.matches vérifie si une chaîne donnée correspond à une expression régulière. Une petite expérimentation montre que ce n'est pas tout à fait exact, car cette fonction semble correspondre UNIQUEMENT si l'expression régulière fournie correspond à la chaîne ENTIER! Ainsi, changer l'expression régulière ci-dessus ("\\ S") en "^. * \\ S. * $" Fonctionnera comme prévu, bien que ce comportement ne soit pas correctement documenté et semble diverger considérablement de toutes les autres implémentations de correspondance de chaînes en utilisant des expressions régulières.
Rob Raisch
4

Cette réponse se concentre davantage sur la note latérale " c'est-à-dire qu'elle a au moins un caractère alphanumérique ". En plus de cela, cela n'ajoute pas trop à l'autre solution (antérieure), sauf que cela ne vous fait pas de mal avec NPE au cas où la chaîne le serait null.

Nous voulons falsesi (1) s est nullou (2) s est vide ou (3) s ne contient que des whitechars.

public static boolean containsNonWhitespaceChar(String s) {
  return !((s == null) || "".equals(s.trim()));
}
Andreas Dolk
la source
4

Si vous ne vérifiez que les espaces et que vous ne vous souciez pas de null, vous pouvez utiliser org.apache.commons.lang.StringUtils.isWhitespace (String str),

StringUtils.isWhitespace(String str);

(Vérifie si la chaîne ne contient que des espaces.)

Si vous souhaitez également vérifier la valeur nulle (y compris les espaces), alors

StringUtils.isBlank(String str);
Arun
la source
isBlank (String) est recommandé car il gère également la validation nulle!
Sachidananda Naik le
2

Avec Java-11 +, vous pouvez utiliser l' String.isBlankAPI pour vérifier si la chaîne donnée n'est pas entièrement composée d'espaces -

String str1 = "    ";
System.out.println(str1.isBlank()); // made up of all whitespaces, prints true

String str2 = "    a";
System.out.println(str2.isBlank()); // prints false

Le javadoc pour le même est:

/**
 * Returns {@code true} if the string is empty or contains only
 * {@link Character#isWhitespace(int) white space} codepoints,
 * otherwise {@code false}.
 *
 * @return {@code true} if the string is empty or contains only
 *         {@link Character#isWhitespace(int) white space} codepoints,
 *         otherwise {@code false}
 *
 * @since 11
 */
public boolean isBlank()
Naman
la source
1

La méthode de coupe devrait bien fonctionner pour vous.

http://download.oracle.com/docs/cd/E17476_01/javase/1.4.2/docs/api/java/lang/String.html#trim ()

Renvoie une copie de la chaîne, en omettant les espaces de début et de fin. Si cet objet String représente une séquence de caractères vide, ou si les premier et dernier caractères de la séquence de caractères représentés par cet objet String ont tous deux des codes supérieurs à '\ u0020' (le caractère espace), une référence à cet objet String est renvoyée.

Sinon, s'il n'y a pas de caractère avec un code supérieur à '\ u0020' dans la chaîne, un nouvel objet String représentant une chaîne vide est créé et renvoyé.

Sinon, soit k l'index du premier caractère de la chaîne dont le code est supérieur à '\ u0020', et soit m l'index du dernier caractère de la chaîne dont le code est supérieur à '\ u0020'. Un nouvel objet String est créé, représentant la sous-chaîne de cette chaîne qui commence par le caractère à l'index k et se termine par le caractère à l'index m-c'est-à-dire le résultat de this.substring (k, m + 1).

Cette méthode peut être utilisée pour couper les espaces à partir du début et de la fin d'une chaîne; en fait, il supprime également tous les caractères de contrôle ASCII.

Renvoie: Une copie de cette chaîne avec les espaces blancs de début et de fin supprimés, ou cette chaîne s'il n'y a pas d'espace blanc de début ou de fin.

Vous pouvez couper et comparer à une chaîne vide ou vérifier la longueur pour 0.

Corey Ogburn
la source
Le lien de réponse est mort - 404 | Nous sommes désolés, la page n'existe pas ou n'est plus disponible .
Pang
0

Alternative:

boolean isWhiteSpaces( String s ) {
    return s != null && s.matches("\\s+");
 }
OscarRyz
la source
1
\\ s * correspondra à toutes les chaînes avec ou sans espaces. Peut-être voulez-vous dire \\ s +?
Rob Raisch
0

trim () et les autres expressions régulières mentionnées ne fonctionnent pas pour tous les types d'espaces blancs

ie: Caractère Unicode 'LINE SEPARATOR' http://www.fileformat.info/info/unicode/char/2028/index.htm

Fonctions Java Character.isWhitespace () couvre toutes les situations.

C'est pourquoi la solution déjà mentionnée StringUtils.isWhitespace (String) / ou StringUtils.isBlank (String) doit être utilisée.

Andreyro
la source
0

Juste une comparaison de performances sur openjdk 13, Windows 10. Pour chacun de ces textes:

"abcd"
"    "
" \r\n\t"
" ab "
" \n\n\r\t   \n\r\t\t\t   \r\n\r\n\r\t \t\t\t\r\n\n"
"lorem ipsum dolor sit amet  consectetur adipisici elit"
"1234657891234567891324569871234567891326987132654798"

exécuté l'un des tests suivants:

// trim + empty
input.trim().isEmpty()

// simple match
input.matches("\\S")

// match with precompiled pattern
final Pattern PATTERN = Pattern.compile("\\S");
PATTERN.matcher(input).matches()

// java 11's isBlank
input.isBlank()

chaque 10.000.000 fois.

Les resultats:

METHOD    min   max   note
trim:      18   313   much slower if text not trimmed
match:   1799  2010   
pattern:  571   662   
isBlank:   60   338   faster the earlier hits the first non-whitespace character

De manière assez surprenante, l'assiette + vide est la plus rapide. Même s'il a besoin de construire le texte coupé. Encore plus rapide que la simple boucle for à la recherche d'un seul caractère non espacé ...

EDIT: Plus le texte est long, plus les nombres diffèrent. La découpe d'un long texte prend plus de temps qu'une simple boucle. Cependant, les expressions régulières sont toujours la solution la plus lente.

Martlin
la source
0

Alors que personnellement, je préférerais !str.isBlank(), comme d'autres l'ont déjà suggéré (ou en str -> !str.isBlank()tant que prédicat), une version plus moderne et efficace de l' str.trim()approche mentionnée ci-dessus, utiliser str.strip()- en considérant les valeurs nulles comme des "espaces":

if (str != null && str.strip().length() > 0) {...}

Par exemple en tant que prédicat, à utiliser avec des flux, par exemple dans un test unitaire:

@Test
public void anyNonEmptyStrippedTest() {
    String[] strings = null;
    Predicate<String> isNonEmptyStripped = str -> str != null && str.strip().length() > 0;
    assertTrue(Optional.ofNullable(strings).map(arr -> Stream.of(arr).noneMatch(isNonEmptyStripped)).orElse(true));
    strings = new String[] { null, "", " ", "\\n", "\\t", "\\r" };
    assertTrue(Optional.ofNullable(strings).map(arr -> Stream.of(arr).anyMatch(isNonEmptyStripped)).orElse(true));
    strings = new String[] { null, "", " ", "\\n", "\\t", "\\r", "test" };
}
ourson
la source