第一部分:将网路图片显示到ImageView控件 1 利用图片的路径,得到图片的字节数组 public static byte [] getImage(String path) throws Exception{ URL imageUrl=new URL(path); HttpURLConnection connection=(HttpURLConnection)imageUrl.openConnection(); connection.setConnectTimeout(5000); connection.setRequestMethod("POST"); if(connection.getResponseCode()==200){ InputStream inputStream=connection.getInputStream(); byte [] imageData=GetResource.readResource(inputStream); return imageData; } return null; } 分析: (1)利用URL得到HttpURLConnection connection这样便于资源建立起了联系,且设置connection的属性值 (2)利用HttpURLConnection connection得到输入流.即可以这么想:此时的图片已经保存到了此输入流inputStream里 (3)将在输入流里的图片数据输出到字节数组里面.即byte [] imageData=GetResource.readResource(inputStream).如下 readResource(inputStream)方法如下: public static byte[] readResource(InputStream inputStream) throws Exception{ ByteArrayOutputStream outputStream=new ByteArrayOutputStream(); byte [] buffer=new byte[1024]; int len=0; while( (len=inputStream.read(buffer))!=-1){ outputStream.write(buffer,0,len); } inputStream.close(); outputStream.close(); return outputStream.toByteArray(); } 分析: (1)输入流里不存在方法可以直接将输入流中的数据一次性转换成字符串或者字节数组!!!!!!! 思路:要将输入流里的数据拿出来,需要先将这些数据读到(即常用的read()系列的方法)一个数组里面每次当此数组满的时候 再由一个输出流将数据里的数据写到(即常用的writer()系列的方法)输出流里面!!!这里的数组就相当于一个物品搬运的 中转站,起到了一个缓冲作用. (2)待数据全部转移到输入流outputStream里面,此时就可以把输出流的数据全部转换为字节数组,即outputStream.toByteArray(); (3)在此例子就很好体现了输入流和输出流的使用. 在输入流相应的API中都是把输入流里的数据读取到一个数组中,或者只读取一个字节,或者读取一行 如FileInputStream类中的方法: public int read(byte[] b,int off,int len)从此输入流中将最多 len 个字节的数据读入一个字节数组中 public int read()从此输入流中读取一个数据字节 如在BufferedReader类中的方法: public String readLine() 读取一个文本行.返回值:包含该行内容的字符串 在输出流相应的API中都把是字节数组里的数据写入此输出流,或者只把数组中的某个位置的数据写入输出流 如ByteArrayOutputStream类的方法中: public void write(byte[] b,int off,int len)将指定字节数组中从偏移量off开始的len个字节写入此字节数组输出流 public void write(int b)将指定的字节写入此字节数组输出流 然后我们可以发现: (1)可以把输出流里的数据转换为字节数组 如ByteArrayOutputStream类的方法中: public byte[] toByteArray():创建一个新分配的字节数组。其大小是此输出流的当前大小,并且缓冲区的有效内容已复制到该数组中。 (2)可以把输出流里的数据转换为字符串 如ByteArrayOutputStream类的方法中: public String toString():将缓冲区的内容转换为字符串,根据平台的默认字符编码将字节转换成字符。 2 生成位图且利用ImageView进行显示 byte [] imageData=GetImageResource.getImage(path); Bitmap bitmap=BitmapFactory.decodeByteArray(imageData, 0, imageData.length); imageView.setImageBitmap(bitmap); 第二部分:本地照片的复制 package cn.io; //FileInputStream和FileOutputStream实现照片 //注意图片不可以用字符流(如FileReader和FileWriter)拷贝,因为它会去查找字符表 //在方式二中使用InputStream中的available()方法建立缓冲区 //方式二的好处是不用循环操作,直接先全部暂存在一个数组里,然后再全部取出存到目的地 import java.io.*; public class CopyPhoto{ public static void main(String[] args) throws Exception{ FileInputStream fis=null; FileOutputStream fos=null; //…………………………………………以下为方式一 fis=new FileInputStream("F:\\1.JPG"); fos=new FileOutputStream("F:\\2.JPG"); byte [] temp1=new byte[1024*1024]; int length=0; while((length=fis.read(temp1))!=-1){ fos.write(temp1, 0, length); fos.flush(); } //…………………………………………以下为方式二 fis=new FileInputStream("F:\\3.JPG"); fos=new FileOutputStream("F:\\4.JPG"); byte [] temp2=new byte[fis.available()]; fis.read(temp2); fos.write(temp2); fis.close(); fos.close(); } }
补遗(2014年1月23日21:17:53)
http://blog.csdn.net/lfdfhl/article/details/8195375
注意输出流的理解:它都是把数据写到输出流里面.
参见该博客的一些说明.
既然把数据写在了输出流里面了.那么它一定是有用的!那么它不可能一直呆在输出流里面,这样的话一点实际意义都没有了.
至于在输出流里的数据怎么用,用在哪里.当然要看实际情况了.
无非是两种:
1 第一种情况.输出流和硬盘打交道.输出流和硬盘或者SD卡连在一起的.比如例子中的复制照片的.
即代码fos=new FileOutputStream("F:\\2.JPG");
然后把字节数组里面的数据写到了输出流即代码 fos.write(temp1, 0, length);
因为这个输出流直接联系的所以数据直接就到了硬盘了.
2 第二种情况.输出流和内存打交道.
比如例子中关于Bitmap显示网络图片的例子.
这个时候在内存中要使用输入流的数据.于是把输入流的数据写入到了输出流
准确地来说是一个ByteArrayOutputStream字节数组输出流.
ByteArrayOutputStream的目的就是在内存中创建缓冲区,也就是把数据都保存在了内存中的ByteArrayOutputStream.
然后我们可以用outputStream.toByteArray()把数据保存到了内存中的字节数组中.
我们看一下OutputStream的子类 ByteArrayOutputStream, FileOutputStream, FilterOutputStream, ObjectOutputStream,
OutputStream, PipedOutputStream
其实常用的就是前两个ByteArrayOutputStream, FileOutputStream 分别对应于内存和硬盘的操作.
在资料:http://blog.sina.com.cn/s/blog_4c1c2d43010007sg.html中提到:
OutputStream的类决定了输出所要去往的目标,这个目标包括I.字节数组 II.文件 III.管道
我觉得这个说法还是挺形象和准确的.