2012-02-13 22 views
15

क्योंकि MySQL 5.1 4 बाइट यूटीएफ -8 अनुक्रमों का समर्थन नहीं करता है, मुझे इन तारों में 4 बाइट अनुक्रमों को प्रतिस्थापित/ड्रॉप करने की आवश्यकता है।जावा में एक यूटीएफ -8 स्ट्रिंग से 4 (+) - बाइट वर्णों को प्रतिस्थापित/निकालने के लिए कैसे?

मैं इन पात्रों को बदलने के लिए एक साफ रास्ता देख रहा हूँ।

अपाचे पुस्तकालयों में एक प्रश्न चिह्न के साथ पात्रों की जगह कर रहे हैं, इस मामले के लिए ठीक है, हालांकि ASCII बराबर निश्चित रूप से अच्छे, हो जाएगा।

एनबी। इनपुट बाहरी स्रोतों (ई-मेल नाम) से है और डेटाबेस को अपग्रेड करना इस बिंदु पर समय पर समाधान नहीं है।

+1

आप मजाक कर रहे हैं। MySQL अभी भी इस दिन और उम्र में यूनिकोड का समर्थन नहीं करता है? यह बेहोश है। यह दर्शाते हुए कि आप यूनिकोड का समर्थन करते हैं जब आप केवल 1-, 2-, या 3-बाइट यूटीएफ -8 अनुक्रमों को संभाल सकते हैं, यह कहकर एक बड़ा झूठ है कि आप यूनिकोड का समर्थन करते हैं जब आप केवल 1-बाइट ASCII अनुक्रमों का समर्थन करते हैं। या तो आप किसी भी कानूनी यूनिकोड कोड बिंदु का समर्थन करते हैं, या आप यूनिकोड का समर्थन नहीं करते हैं। यह एक बाइनरी चीज है। MySQL जैसे लगता है यूनिकोड का समर्थन नहीं करता है। कृपया मुझे कहें कि यह एक मज़ाक है। – tchrist

+2

@tchrist: MySQL 5.5.3 और ऊपर उचित UTF-8 का समर्थन नई 'utf8mb4 "" वर्ण सेट "के माध्यम से (http://dev.mysql.com/doc/refman/5.5/en/charset-unicode.html) । हालांकि, "utf8" "वर्ण सेट" केवल 3-बाइट यूटीएफ -8 मल्टीबाइट वर्णों का समर्थन करता है, जो कि विभिन्न MySQL संस्करणों के बीच प्रतिकृति समस्याओं को रोकने के लिए है। भविष्य में MySQL रिलीज में "utf8" "utf8mb4" के लिए उपनाम में बदल सकता है। – ninjalj

+0

[इस सवाल] के समान (http://stackoverflow.com/questions/8491431/remove-4-byte-characters-from-a-utf-8-string) सिवाय इसके कि यह जावा के बजाए PHP में समाधान का अनुरोध कर रहा है। यूटीएफ -8 में –

उत्तर

10

हमने इस समस्या के लिए जावा में निम्न विधि को कार्यान्वित करना समाप्त कर दिया। बेसिकल ने उच्च कोडपॉइंट वाले अक्षर को अंतिम 3byte UTF-8 char के साथ बदल दिया।

ऑफसेट गणना यकीन है कि हम यूनिकोड कोड अंक पर रहने बनाने के लिए कर रहे हैं।

public static final String LAST_3_BYTE_UTF_CHAR = "\uFFFF"; 
public static final String REPLACEMENT_CHAR = "\uFFFD"; 

public static String toValid3ByteUTF8String(String s) { 
    final int length = s.length(); 
    StringBuilder b = new StringBuilder(length); 
    for (int offset = 0; offset < length;) { 
     final int codepoint = s.codePointAt(offset); 

     // do something with the codepoint 
     if (codepoint > CharUtils.LAST_3_BYTE_UTF_CHAR.codePointAt(0)) { 
      b.append(CharUtils.REPLACEMENT_CHAR); 
     } else { 
      if (Character.isValidCodePoint(codepoint)) { 
       b.appendCodePoint(codepoint); 
      } else { 
       b.append(CharUtils.REPLACEMENT_CHAR); 
      } 
     } 
     offset += Character.charCount(codepoint); 
    } 
    return b.toString(); 
} 
+0

धन्यवाद। मैंने अपने पूरे MySQL चरित्र सेट को बदलने से बचने के लिए इसका इस्तेमाल किया। मुझे अपने डेटा में विदेशी चरित्र या पू चरित्र की आवश्यकता नहीं है। – Robert

2

5 बाइट UTF-8 दृश्यों के साथ शुरू एक 111110xx-बाइट और 6 बाइट UTF-8 दृश्यों एक 1111110x-बाइट के साथ शुरू करते हैं। ध्यान देने योग्य है कि, 1-4-बाइट यूटीएफ -8 अनुक्रमों के अनुवर्ती बाइट्स में बाइट्स शामिल नहीं हैं क्योंकि फॉलो-अप बाइट हमेशा 10xxxxxx रूप के होते हैं।

इसलिए तुम सिर्फ बाइट्स के माध्यम से जा सकते हैं और हर बार आप देख तरह 111110xx की एक बाइट तो केवल एक फेंकना '?' इनपुट से अगले 4 बाइट छोड़ते समय आउटपुट-स्ट्रीम/सरणी में; 6-बाइट-अनुक्रमों के लिए एनालॉग।

+2

5 और 6-बाइट अनुक्रम अमान्य हैं - यह कहना नहीं है कि वे स्रोत टेक्स्ट में प्रकट नहीं हो सकते हैं। –

+0

हाँ सुरक्षित होने के लिए सबसे अच्छा –

+0

यदि 5 और 6 बाइट अनुक्रम कानूनी नहीं हैं तो वे किसी भी समस्या से कम होना चाहिए। मेरी समस्या वर्तमान में 4byte अनुक्रमों के साथ है जो कानूनी रूप से अभी तक mysql द्वारा समर्थित नोग हैं। – pvgoddijn

4

एक और सरल समाधान नियमित अभिव्यक्ति [^\u0000-\uFFFF] का उपयोग करना है। उदाहरण के लिए जावा में:

text.replaceAll("[^\\u0000-\\uFFFF]", "\uFFFD"); 
+0

धन्यवाद, उत्कृष्ट उत्तर – tjeubaoit

संबंधित मुद्दे