2013-07-02 2 views
0

Я получаю сообщение об ошибке при попытке проверить хэш MD5 файла.Проверка MD5 файла

Файл, notice.txt имеет следующее содержание:

My name is sanjay yadav . i am in btech computer science .>> 

Когда я проверил онлайн с onlineMD5.com он дал MD5, как: 90F450C33FAC09630D344CBA9BF80471.

Мой выход программы:

My name is sanjay yadav . i am in btech computer science . 
Read 58 bytes 
d41d8cd98f00b204e9800998ecf8427e 

Вот мой код:

import java.io.*; 
import java.math.BigInteger; 
import java.security.DigestException; 
import java.security.MessageDigest; 
import java.security.NoSuchAlgorithmException; 

public class MsgDgt { 
    public static void main(String[] args) throws IOException, DigestException, NoSuchAlgorithmException { 

     FileInputStream inputstream = null; 
     byte[] mybyte = new byte[1024]; 

     inputstream = new FileInputStream("e://notice.txt"); 
     int total = 0; 
     int nRead = 0; 
     MessageDigest md = MessageDigest.getInstance("MD5"); 
     while ((nRead = inputstream.read(mybyte)) != -1) { 
      System.out.println(new String(mybyte)); 
      total += nRead; 
      md.update(mybyte, 0, nRead); 
     } 

     System.out.println("Read " + total + " bytes"); 
     md.digest(); 
     System.out.println(new BigInteger(1, md.digest()).toString(16)); 
    } 
} 
+0

возможно дубликат [Получение MD5 Checksum виде файла в Java] (http://stackoverflow.com/questions/ 304268/get-a-files-md5-checksum-in-java) – Simon

+0

Я не буду полагаться на этот сайт сейчас .. Я думаю, что результат 2f4c6a40682161e5b01c24d5aa896da0 правильный ... вы пропустили один ноль в последнем .. (пожалуйста, проверьте его). Содержание: «Меня зовут санджай йадав, я нахожусь в информатике btech». – Bitopan

ответ

1

Там ошибка в коде и Я считаю, онлайн-инструмент дает неправильный ответ. Здесь вы в настоящее время вычисления дайджеста дважды:

md.digest(); 
System.out.println(new BigInteger(1, md.digest()).toString(16)); 

Каждый раз, когда вы звоните digest(), он сбрасывает внутреннее состояние. Вы должны удалить первый звонок до digest(). Это потом оставляет вас с этим, как дайджест:

2f4c6a40682161e5b01c24d5aa896da0 

Это тот же результат, я получаю от C#, и я считаю, что это правильно. Я не знаю, почему онлайн-чекер дает неверный результат. (Если вы поместите его в текст части одного и того же сайта, что дает правильный результат.)

Пару других точек на вашем коде, хотя:

  • Вы используете платформу кодирование по умолчанию при преобразовании байтов в строку. Я бы сильно отговорил вас от этого.
  • В настоящее время вы преобразовываете буфер в целом в строку, а не только бит, который вы прочитали.
  • Мне не нравится использовать BigInteger как способ преобразования двоичных данных в шестнадцатеричный. Вам, возможно, нужно наложить его на 0, и в основном это не тот класс, для которого был разработан класс. Используйте выделенный шестнадцатеричный класс преобразования, например. из Apache Commons Codec (или различных ответов переполнения стека, которые предоставляют отдельные классы для этой цели).
  • Вы не закрываете входной поток. Вы должны сделать это в finally блоке, или с использованием примерочных с-ресурсов заявление в Java 7.
+0

Я почесал его, и он работает. – Bitopan

+0

Я не буду полагаться на этот сайт сейчас .. Я думаю, что результат 2f4c6a40682161e5b01c24d5aa896da0 правильный ... вы пропустили один ноль в последнем .. (пожалуйста, проверьте его). Содержание: «Меня зовут санджай йадав, я нахожусь в информатике btech». – Bitopan

+0

@Bitopan: Да, только ошибка C & P. –

0

Я использую эту функцию:

public static String md5Hash(File file) { 
    try { 
     MessageDigest md = MessageDigest.getInstance("MD5"); 
     InputStream is = new FileInputStream(file); 
     byte[] buffer = new byte[1024]; 

     try { 
      is = new DigestInputStream(is, md); 

      while (is.read(buffer) != -1) { } 
     } finally { 
      is.close(); 
     } 

     byte[] digest = md.digest(); 

     BigInteger bigInt = new BigInteger(1, digest); 
     String output = bigInt.toString(16); 
     while (output.length() < 32) { 
      output = "0" + output; 
     } 

     return output; 
    } catch (NoSuchAlgorithmException e) { 
     e.printStackTrace(); 
    } catch (FileNotFoundException e) { 
     e.printStackTrace(); 
    } catch (IOException e) { 
     e.printStackTrace(); 
    } 

    return null; 
} 
+0

Зачем вам нужно создавать новый массив байтов для каждого вызова 'read'? Мне кажется немного извилистым, так как использует «BigInteger» для шестнадцатеричных преобразований (а не код, который предназначен для преобразования байтового массива в шестнадцатеричный). Обработка исключений тоже вызывает беспокойство ... –

+0

На самом деле, я не уверен, что теперь вся функция должна думать об этом. Это был пример, который я нашел в Интернете.Хотя, я не уверен, что проблема с использованием BigInteger, что бы вы сделали вместо этого? Я полностью согласен с объявлением массива байтов. – Knossos

+0

Я бы использовал что-то вроде Apache Commons Codec или нашел ответ на один из многих вопросов «как мне преобразовать байты в шестую» в Stack Overflow. –

Смежные вопросы