2012-01-05 19 views
11

Tôi phải kiểm tra xem chuỗi có được bao gồm trong chuỗi khác hay không nhưng không tính đến trường hợp hoặc dấu trọng âm (dấu tiếng Pháp trong trường hợp này).có chứa collator

Ví dụ: hàm phải trả về true nếu tôi tìm kiếm "rhone" trong chuỗi "Vallée du Rhône".

Bộ cộng hưởng hữu ích cho việc so sánh chuỗi có dấu trọng âm nhưng không cung cấp chức năng contains.

Có cách nào dễ dàng để thực hiện công việc không? Một regex có thể?

thông tin bổ sung:
Tôi chỉ cần một giá trị trả về true/false, tôi không quan tâm đến số lượng các trận đấu hoặc vị trí của chuỗi thử nghiệm trong chuỗi tham khảo.

+0

Thật không may, java.util.regex không hỗ trợ đối chiếu trình tự, nếu không bạn có thể đã thực sự cố gắng và trận đấu với '\ brh [[= o =]] ne \ b' ... – fge

Trả lời

16

Bạn có thể sử dụng Normalizer để giảm chuỗi thành phiên bản rút gọn mà bạn có thể so sánh trực tiếp.

Edit: phải rõ ràng

String normalized = Normalizer.normalize(text, Normalizer.Form.NFD); 
String ascii = normalized.replaceAll("[^\\p{ASCII}]", ""); 
0

Cách thông thường để làm điều này là để chuyển đổi tất cả các chuỗi thành chữ thường không có dấu, và sau đó sử dụng các tiêu chuẩn 'chứa'.

10

Hãy xem Normalizer.

Bạn nên gọi số đó là Normalizer.Form.NFD làm đối số thứ hai của mình.

Vì vậy, đó sẽ là:

Normalizer.normalize(yourinput, Normalizer.Form.NFD) 
    .replaceAll("\\p{InCombiningDiacriticalMarks}+", "") 
    .toLowerCase() 
    .contains(yoursearchstring) 

đó sẽ trở thành sự thật nếu trận đấu (và, tất nhiên, false)

+1

Sẽ không này phân hủy 'è' thành 'e''? Điều đó sẽ làm cho() thất bại trừ khi ký tự có dấu luôn luôn là ký tự cuối cùng của chuỗi. – Viruzzo

+0

Rất tiếc! Chính xác. Đã sửa. – fge

3

Làm thế nào về điều này?

private static final Pattern ACCENTS_PATTERN = Pattern.compile("\\p{InCombiningDiacriticalMarks}+"); 

public static boolean containsIgnoreCaseAndAccents(String haystack, String needle) { 
    final String hsToCompare = removeAccents(haystack).toLowerCase(); 
    final String nToCompare = removeAccents(needle).toLowerCase(); 

    return hsToCompare.contains(nToCompare); 
} 

public static String removeAccents(String string) { 
    return ACCENTS_PATTERN.matcher(Normalizer.normalize(string, Normalizer.Form.NFD)).replaceAll(""); 
} 

public static void main(String[] args) { 
    System.out.println(removeAccents("Vallée du Rhône")); 
    System.out.println(removeAccents("rhone")); 
    System.out.println(containsIgnoreCaseAndAccents("Vallée du Rhône", "rhone")); 

} 
Các vấn đề liên quan