import java.io.*;
//BASE64 code 4 file
public class Base64
{
static String BaseTable[] = {
"A","B","C","D","E","F","G","H","I","J","K","L","M","N","O","P",
"Q","R","S","T","U","V","W","X","Y","Z","a","b","c","d","e","f",
"g","h","i","j","k","l","m","n","o","p","q","r","s","t","u","v",
"w","x","y","z","0","1","2","3","4","5","6","7","8","9","+","/"
};
public static void main(String[] args)
{
File f = new File("www");;
try
{
FileInputStream out = new FileInputStream(f);
byte[] b = new byte[(byte)f.length()]; //我要编码的目标文件的长度(字节数)作为byte数组的容量
int n = out.read(b); //读出文件的字节数
if (n < 1) //没有内容
return;
//System.out.println(n + " " + f.length());
byte[] buf = new byte[4]; //base64字符数组
int n3byt = n / 3; //3 bytes 组的个数, 3个字节分为一组(注意: 一个英文字母是一个字节, 一个汉字是2个字节)
int nrest = n % 3; //分组后剩余 bytes
int k = n3byt * 3; //n3byt这些组实际的大小
int linelength = 0; // 行长
int i = 0; // 指针
//3-bytes分组, 把3个8字节的变成6个4字节的
while (i < k)
{
//0xFC对应的二进制是11111100, 意思就是取前6位(因为b[i]的后2位被0与掉了), >>2表示右移2位, 即取前6位
buf[0] = (byte)((b[i] & 0xFC) >> 2);
/*0x03对应的二进制是00000011, 即留前一个字符b[i]的后2位, 要左移4位, 以便给下4位留个地方;
0xF0对应的二进制是11110000, 取当前数的前4位作为6位数的后4位, 所以利用>>4, 和前一个数的后2位结合就是共6位了*/
buf[1] = (byte)(((b[i] & 0x03) << 4) | ((b[i+1] & 0xF0) >> 4));
//类似上面的, 取bytes[i+1]后4位作为高4位, 取bytes[i+2]前2为作为低2位
buf[2] = (byte)(((b[i+1] & 0x0F) << 2) | ((b[i+2] & 0xC0) >> 6));
//最后的低6位作为最后的6位
buf[3] = (byte)( b[i+2] & 0x3F);
System.out.println("After base64 encode: ");
System.out.println("buf[0] is: " + BaseTable[buf[0]]);
System.out.println("buf[1] is: " + BaseTable[buf[1]]);
System.out.println("buf[2] is: " + BaseTable[buf[2]]);
System.out.println("buf[3] is: " + BaseTable[buf[3]]);
//处理尾部
if (nrest==2) //最后还剩2个字节, 差1个字节
{
buf[0] = (byte)(( b[k] & 0xFC) >> 2); //注意啊, 是从k开始的
buf[1] = (byte)(((b[k] & 0x03) << 4) | ((b[k+1] & 0xF0) >> 4));
buf[2] = (byte)(((b[i+1] & 0x0F) << 2)); //低4位左移2位变成了6位, 左移会在低2位自动补0的
}
else if (nrest==1) //最后还剩1个字节, 差2个字节
{
buf[0] = (byte)((b[k] & 0xFC) >> 2);
buf[1] = (byte)((b[k] & 0x03) << 4); //低2位左移4位变成了6位
}
if (nrest > 0) //发送尾部, nrest > 0说明是那些构不成一组(一组是3个字节)的
{
//即使只有一个字符, 也会肯定输出buf[0]和buf[1]的, 因为一个字符8位可以拆成2个6位的字符
System.out.println("buf[0] is: " + BaseTable[buf[0]]);
System.out.println("buf[1] is: " + BaseTable[buf[1]]);
if (nrest==2)
System.out.println("buf[2] is: " + BaseTable[buf[2]]);
else
System.out.println("buf[2] is: =");
//会肯定输出一个=号的, 因为nrest > 0
System.out.println("buf[3] is: =");
}
i+=3;
}
}
catch(FileNotFoundException e){e.printStackTrace();}
catch(IOException e){e.printStackTrace();}
}
}