[英]Check that string contains a character from array
我想检查作为文件名的字符串是否包含来自ILLEGAL_CHARACTERS
的非法参数。 我可以简单地使用 for 循环,但我想通过Streams来做到这一点。
我的代码:
package shared;
import java.util.Arrays;
public class Validator {
private static final Character[] ILLEGAL_CHARACTERS =
{'/','\n','\r','\t','\0','\f','`','?','*','\\','<','>','|','\"',':'};
public static boolean fileNameIsValid(String fileName) {
return Arrays.stream(ILLEGAL_CHARACTERS).anyMatch(fileName::contains);
}
}
问题在于 contains 方法因为它需要一个CharSequence
而不是char
。 stream 有什么方法可以做到这一点,而无需将Character[]
类型更改为String[]
?
Streams 在这里可能不是最合适的。 此外,现在您的解决方案具有二次复杂度(N*M,其中 N 是文件名长度,M 是非法字符数组的大小),性能不是很好。 正如评论中所建议的,您可以使用正则表达式:
private static final Pattern ILLEGAL_CHARACTERS_REGEX =
Pattern.compile("[/\n\r\t\0\f`?*\\\\<>|\":]");
public static boolean fileNameIsValidRegex(String fileName) {
return !ILLEGAL_CHARACTERS_REGEX.matcher(fileName).find();
}
或者,如果您的非法字符集仅限于 ASCII,您可以使用 bitset 来提高性能:
private static final BitSet ILLEGAL_CHARACTERS = new BitSet();
static {
for (char c : new char[]{
'/','\n','\r','\t','\0','\f','`','?','*','\\','<','>','|','\"',':'}) {
ILLEGAL_CHARACTERS.set(c);
}
}
public static boolean fileNameIsValid(String fileName) {
return fileName.chars().noneMatch(ILLEGAL_CHARACTERS::get);
}
您可以尝试使用indexOf
:
return Arrays.stream(ILLEGAL_CHARACTERS)
.map(fileName::indexOf)
.anyMatch(i -> i >= 0);
首先,我建议您使用Set
而不是数组,因为您不需要索引您的东西,然后 Stream 覆盖给定字符串中的字符,并检查是否与您的集合匹配。
从字符串上的chars()
方法获取字符,这将为您提供一个整数数组,然后您可以将其转换为一个字符“数组”
这就是你所需要的:
private static final Set<Character> ILLEGAL_CHARACTERS = Set.of(
'/','\n','\r','\t','\0','\f','`','?','*','\\','<','>','|','\"',':');
public static boolean fileNameIsValid(String fileName) {
return fileName.chars()
.mapToObj(c -> (char) c)
.noneMatch(ILLEGAL_CHARACTERS::contains);
}
如果contains
方法需要一个CharSequence
而不是char
,那么你可以给它:
Arrays.stream(ILLEGAL_CHARACTERS)
.map(String::valueOf)
.anyMatch(fileName::contains);
但在String
class 的内部,此方法使用indexOf(String str)
方法:
public boolean contains(CharSequence s) {
return indexOf(s.toString()) > -1;
}
所以,为了避免多余的类型转换,你可以使用另一个indexOf(int ch)
方法:
Arrays.stream(ILLEGAL_CHARACTERS).anyMatch(ch -> fileName.indexOf(ch) > -1);
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.