המרה בין מערכי בתים למחרוזות הקסדצימליות בג'אווה

1. סקירה כללית

במדריך זה נבחן דרכים שונות להמיר מערך בתים להקסדצימלי חוּט, ולהיפך.

נבין גם את מנגנון ההמרה ונכתוב את היישום שלנו כדי להשיג זאת.

2. המרה בין בתים להקסדצימלי

קודם כל, בואו נסתכל על לוגיקת ההמרה בין בתים למספרים הקסדצימאליים.

2.1. בתים להקסדצימלי

הבייטים הם מספרים שלמים של 8 סיביות חתומים ב- Java. לכן, אנחנו צריכים להמיר כל קטע של 4 סיביות ל- hex בנפרד ולשרשר אותם. כתוצאה מכך נקבל שני תווים הקסדצימליים לאחר ההמרה.

למשל, אנו יכולים לכתוב 45 כ- 0010 1101 בבינארי, והמקבילה ההקסדצימאלית תהיה "2d":

0010 = 2 (בסיס 10) = 2 (בסיס 16) 1101 = 13 (בסיס 10) = d (בסיס 16) לכן: 45 = 0010 1101 = 0x2d 

בואו נשתמש בהיגיון הפשוט הזה ב- Java:

מחרוזת ציבורית byteToHex (byte num) {char [] hexDigits = char חדש [2]; hexDigits [0] = Character.forDigit ((מספר >> 4) & 0xF, 16); hexDigits [1] = Character.forDigit ((num & 0xF), 16); להחזיר מחרוזת חדשה (hexDigits); }

כעת, בואו נבין את הקוד הנ"ל על ידי ניתוח כל פעולה. קודם כל, יצרנו מערך char באורך 2 לאחסון הפלט:

char [] hexDigits = char [2] חדש;

לאחר מכן, בידדנו סיביות מסדר גבוה יותר על ידי העברת ימינה של 4 סיביות. ואז, החלנו מסכה כדי לבודד 4 סיביות מסדר נמוך. מיסוך נדרש מכיוון שמספרים שליליים מיוצגים באופן פנימי כתוספת של שני למספר החיובי:

hexDigits [0] = Character.forDigit ((מספר >> 4) & 0xF, 16);

לאחר מכן אנו ממירים את 4 הסיביות הנותרות להקסדצימלי:

hexDigits [1] = Character.forDigit ((num & 0xF), 16);

לבסוף, אנו יוצרים a חוּט אובייקט ממערך הצ'ר. ואז, החזיר אובייקט זה כמערך הקסדצימלי שהומר.

עכשיו, בואו להבין איך זה יעבוד עבור בתים שליליים -4:

hexDigits [0]: 1111 1100 >> 4 = 1111 1111 1111 1111 1111 1111 1111 1111 1111 1111 1111 1111 1111 1111 1111 1111 & 0xF = 0000 0000 0000 0000 0000 0000 0000 1111 = 0xf hexDigits [1]: 1111 1100 & 0xF = 0000 1100 = 0xc לכן: -4 (בסיס 10) = 1111 1100 (בסיס 2) = fc (בסיס 16)

ראוי גם לציין כי אופי.forDigit() השיטה מחזירה תמיד תווים קטנים.

2.2. הקסדצימלי לבייט

עכשיו, בואו להמיר ספרה הקסדצימאלית לבייט. כידוע, בתים מכילים 8 ביטים. לָכֵן, אנו זקוקים לשתי ספרות הקסדצימליות כדי ליצור בית אחד.

קודם כל, נמיר כל ספרה הקסדצימאלית לשווה ערך בינארי בנפרד.

ואז עלינו לשרשר את שני ארבעת קטעי הסיביות כדי לקבל את המקבילה של בתים:

הקסדצימלי: 2d 2 = 0010 (בסיס 2) d = 1101 (בסיס 2) לכן: 2d = 0010 1101 (בסיס 2) = 45

עכשיו, בואו נכתוב את הפעולה ב- Java:

בתים ציבוריים hexToByte (מחרוזת hexString) {int firstDigit = toDigit (hexString.charAt (0)); int secondDigit = toDigit (hexString.charAt (1)); return (byte) ((firstDigit << 4) + secondDigit); } פרטי int toDigit (char hexChar) {int digit = Character.digit (hexChar, 16); if (digit == -1) {throw new IllegalArgumentException ("תו הקסדצימלי לא חוקי:" + hexChar); } ספרת החזרה; }

בואו נבין את זה, פעולה אחת בכל פעם.

קודם כל, המירו תווים הקסדצימליים למספרים שלמים:

int firstDigit = toDigit (hexString.charAt (0)); int secondDigit = toDigit (hexString.charAt (1));

ואז עזבנו את הספרה המשמעותית ביותר בארבעה ביטים. כתוצאה מכך, לייצוג הבינארי יש אפסים בארבעה ביטים משמעותיים לפחות.

ואז הוספנו לה את הספרה הכי פחות משמעותית:

return (byte) ((firstDigit << 4) + secondDigit);

עכשיו, בואו נבחן את toDigit () שיטה מקרוב. אנו משתמשים ב- Character.digit () שיטה להמרה. אם ערך התו המועבר לשיטה זו אינו ספרה חוקית ברדיקס שצוין, -1 מוחזר.

אנו מאמתים את ערך ההחזרה ומציגים חריג אם עבר ערך לא חוקי.

3. המרה בין מערכי בתים להקסדצימלי מיתרים

בשלב זה אנו יודעים להמיר בתים להקסדצימלי, ולהיפך. בואו נרחיב את האלגוריתם הזה ונמיר מערך בתים מ / מההקסדצימלי חוּט.

3.1. מערך בתים להקסדצימלי חוּט

עלינו לעבור דרך המערך וליצור זוג הקסדצימלי לכל בייט:

מחרוזת ציבורי codeHexString (בייט [] byteArray) {StringBuffer hexStringBuffer = StringBuffer חדש (); עבור (int i = 0; i <byteArray.length; i ++) {hexStringBuffer.append (byteToHex (byteArray [i])); } להחזיר hexStringBuffer.toString (); }

כידוע, הפלט תמיד יהיה באותיות קטנות.

3.2. מחרוזת הקסדצימלי למערך בתים

קודם כל, עלינו לבדוק אם אורך ההקסדצימלי חוּט הוא מספר זוגי. הסיבה לכך היא הקסדצימלי חוּט עם אורך מוזר יביא לייצוג בתים שגוי.

כעת נעבור דרך המערך ונמיר כל זוג הקסדצימלי לבייט:

בתים ציבוריים [] decodeHexString (String hexString) {if (hexString.length ()% 2 == 1) {throw new IllegalArgumentException ("מחרוזת הקסדצימאלית לא חוקית סופקה."); } בתים [] בתים = בתים חדשים [hexString.length () / 2]; עבור (int i = 0; i <hexString.length (); i + = 2) {בתים [i / 2] = hexToByte (hexString.substring (i, i + 2)); } להחזיר בתים; }

4. באמצעות ביג-שלם מעמד

אנחנו יכולים ליצור אובייקט מסוג ביג-שלם על ידי העברת מערך חתימה ובתים.

כעת נוכל ליצור את ההקסדצימלי חוּט בעזרת פורמט השיטה הסטטית המוגדר ב חוּט מעמד:

קידוד מחרוזת ציבוריUsingBigIntegerStringFormat (בתים [] בתים) {BigInteger bigInteger = BigInteger חדש (1, בתים); החזר String.format ("% 0" + (בתים. אורך << 1) + "x", ביג-שלם); }

הפורמט המסופק ייצור הקסדצימלי של אפס קטן חוּט. אנו יכולים גם ליצור מחרוזת רישיות על ידי החלפת "x" ב- "X".

לחלופין, היינו יכולים להשתמש ב- toString () שיטה מ ביג-שלם. העדין ההבדל בשימוש ב- toString () השיטה היא שהפלט אינו מרופד באפסים מובילים:

קידוד מחרוזות ציבוריUsingBigIntegerToString (בתים [] בתים) {BigInteger bigInteger = BigInteger חדש (1, בתים); החזר bigInteger.toString (16); }

עכשיו, בואו נסתכל על הקסדצימלי חוּט ל בתים המרת מערך:

בתים ציבוריים [] decodeUsingBigInteger (String hexString) {byte [] byteArray = BigInteger חדש (hexString, 16) .toByteArray (); if (byteArray [0] == 0) {byte [] output = byte new [byteArray.length - 1]; System.arraycopy (byteArray, 1, output, 0, output.length); תפוקת החזר; } להחזיר byteArray; }

ה toByteArray () השיטה מייצרת ביט סימן נוסף. כתבנו קוד ספציפי לטיפול בסיבית נוספת זו.

לפיכך, עלינו להיות מודעים לפרטים אלה לפני שנשתמש ב- ביג-שלם כיתה לגיור.

5. שימוש ב- ממיר DataType מעמד

ה ממיר DataType הכיתה מסופקת עם ספריית JAXB. זה חלק מהספרייה הסטנדרטית עד Java 8. החל מג'אווה 9, עלינו להוסיף java.xml.bind מודול לזמן הריצה במפורש.

בואו נסתכל על היישום באמצעות ה- ממיר DataType מעמד:

קידוד מחרוזת ציבוריUsingDataTypeConverter (בתים [] בתים) {החזר DatatypeConverter.printHexBinary (בתים); } בתים ציבוריים [] decodeUsingDataTypeConverter (String hexString) {return DatatypeConverter.parseHexBinary (hexString); }

כפי שמוצג לעיל, זה מאוד נוח לשימוש ממיר DataType מעמד. ה פלט של printHexBinary () השיטה היא תמיד באותיות רישיות. מחלקה זו מספקת סט של שיטות הדפסה וניתוח להמרת סוג נתונים.

לפני שנבחר בגישה זו, עלינו לוודא שהשיעור יהיה זמין בזמן הריצה.

6. שימוש בספריית Commons-Codec של אפאצ'י

אנחנו יכולים להשתמש ב- הקס מחלקה המסופקת עם ספריית Apache commons-codec:

קידוד מחרוזת ציבוריUsingApacheCommons (בתים [] בתים) זורק DecoderException {להחזיר Hex.encodeHexString (בתים); } בתים ציבוריים [] decodeUsingApacheCommons (String hexString) זורק DecoderException {return Hex.decodeHex (hexString); }

ה תפוקה של encodeHexString נמצא תמיד באותיות קטנות.

7. שימוש בספריית גויאבה של גוגל

בואו נסתכל איך בסיס קידוד class יכול לשמש לקידוד ופענוח מערך בתים להקסדצימלי חוּט:

קידוד מחרוזת ציבוריUsingGuava (בתים [] בתים) {להחזיר BaseEncoding.base16 (). קידוד (בתים); } בתים ציבוריים [] decodeUsingGuava (String hexString) {return BaseEncoding.base16 () .decode (hexString.toUpperCase ()); } 

ה בסיס קידוד מקודד ומפענח באמצעות תווים גדולים כברירת מחדל. אם עלינו להשתמש בתווים קטנים, יש ליצור מופע קידוד חדש בשיטה קטנה.

8. מסקנה

במאמר זה למדנו את אלגוריתם ההמרה בין מערך בתים להקסדצימלי חוּט. דנו גם בשיטות שונות לקידוד מערך בתים למחרוזת hex ולהיפך.

לא מומלץ להוסיף ספרייה לשימוש בכמה שיטות שימוש בלבד. לכן, אם איננו משתמשים כבר בספריות החיצוניות, עלינו להשתמש באלגוריתם הנדון. ה ממיר DataType מחלקה היא דרך נוספת לקודד / לפענח בין סוגי נתונים שונים.

לבסוף, קוד המקור השלם של הדרכה זו זמין ב- GitHub.


$config[zx-auto] not found$config[zx-overlay] not found