首页 文章 精选 留言 我的

精选列表

搜索[谷歌I/O],共10009篇文章
优秀的个人博客,低调大师

Linux 5.12 的 I/O 相关改动

正在开发中的 Linux 5.12 合并了块子系统和相关存储更改的代码,其中值得注意的包括io_uring 、块和驱动的改动。 io_uring 改动的重点是请求回收和 task_work 优化,这些改动可以在大部分是内联的工作中提高 10-20% 的速度。 最初完成这项工作是为了将 io_uring 置于 memcg 下,这增加了相当大的开销,但这是值得的。另一个亮点是 VFS 中的 LOOKUP_CACHED 更改,并为其添加io_uring 支持,这大大加快了文件打开的快速路径。 而在块的改动中,删除的代码多于添加的代码(主要由于Christoph 坚持不懈地追求技术债务的清理),这些改动包括 BFQ 优化、blk-mq 调度器优化、分区写入粒度支持、将 bdev 指针存储在 bio 而不是 gendisk 和 partno 中、 bvec 分配优化等。 在块驱动程序的改动中,大部分是 NVMe 驱动程序的改动,包括避免 nvme-hwmon 中的 devm 分配不能很好地交互、修复no-data命令的nvme-tcp 崩溃、 切换 nvmet-fc、assoc_list 以使用 RCU 保护等。此外,还有针对 MD 代码的 RAID5 修复、BCache 修复,甚至包括久违的软盘驱动程序更新。 按照计划,在 Linux Kernel 5.11 正式发布后,5.12 便会进入合并窗口阶段。然而由于上周的美国严寒天气,实际上直到昨日才有Linux 5.12 代码被推送到 Linux Git 仓库中,不过接下来, Linux 5.12 的合并窗口应该会进入正轨。

优秀的个人博客,低调大师

I/O流的梳理和小结

探索Android软键盘的疑难杂症 深入探讨Android异步精髓Handler 详解Android主流框架不可或缺的基石 站在源码的肩膀上全解Scroller工作机制 Android多分辨率适配框架(1)— 核心基础 Android多分辨率适配框架(2)— 原理剖析 Android多分辨率适配框架(3)— 使用指南 自定义View系列教程00–推翻自己和过往,重学自定义View 自定义View系列教程01–常用工具介绍 自定义View系列教程02–onMeasure源码详尽分析 自定义View系列教程03–onLayout源码详尽分析 自定义View系列教程04–Draw源码分析及其实践 自定义View系列教程05–示例分析 自定义View系列教程06–详解View的Touch事件处理 自定义View系列教程07–详解ViewGroup分发Touch事件 自定义View系列教程08–滑动冲突的产生及其处理 package cc.testio; import android.graphics.Bitmap; import android.graphics.BitmapFactory; import android.os.AsyncTask; import android.os.Bundle; import android.os.Environment; import android.support.v7.app.AppCompatActivity; import android.widget.ImageView; import java.io.BufferedReader; import java.io.BufferedWriter; import java.io.ByteArrayOutputStream; import java.io.File; import java.io.FileInputStream; import java.io.FileOutputStream; import java.io.IOException; import java.io.InputStream; import java.io.InputStreamReader; import java.io.OutputStreamWriter; import java.net.HttpURLConnection; import java.net.URL; /** * * IO流小结: * * 1 InputStream和OutputStream中出和入的方向都是相对于内存而言的. * 读进内存的采用InputStream,写出内存的采用OutputStream * * 2 在使用IO流时请注意区分采用字节流还是字符流 * 比如对于图片的读取就不能采用字符流 * * 3 原来的几篇和IO相关的博文,现已Deprecated * http://blog.csdn.net/lfdfhl/article/details/8195216 * http://blog.csdn.net/lfdfhl/article/details/8195214 * http://blog.csdn.net/lfdfhl/article/details/8195422 * http://blog.csdn.net/lfdfhl/article/details/8195375 * http://blog.csdn.net/lfdfhl/article/details/12174041 * * * 原创作者 * 谷哥的小弟 * * 博客地址 * http://blog.csdn.net/lfdfhl * */ public class MainActivity extends AppCompatActivity { private ImageView mImageView; private DownLoaderAsyncTask mAsyncTask; private String SDCardDir; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); init(); } private void init() { SDCardDir= Environment.getExternalStorageDirectory()+ File.separator; mImageView = (ImageView) findViewById(R.id.imageView); test1(); //test2(); //test3(); //test4(); } /** * * 利用IO流拷贝文本文件 * * 原创作者 * 谷哥的小弟 * * 博客地址 * http://blog.csdn.net/lfdfhl */ private void test1() { // 字节输入流 FileInputStream fileInputStream = null; // 字符输入流 InputStreamReader inputStreamReader = null; // 带缓冲的字符输入流 BufferedReader bufferedReader = null; // 字节输出流 FileOutputStream fileOutputStream = null; // 字符输出流 OutputStreamWriter outputStreamWriter = null; // 带缓冲的字符输出流 BufferedWriter bufferedWriter = null; try { fileInputStream = new FileInputStream(SDCardDir + "test.txt"); //原文件的编码格式为GBK,故在此按该编码方式读取字符避免乱码 inputStreamReader = new InputStreamReader(fileInputStream,"GBK"); bufferedReader = new BufferedReader(inputStreamReader); fileOutputStream = new FileOutputStream(SDCardDir + "eeee.txt"); outputStreamWriter = new OutputStreamWriter(fileOutputStream); bufferedWriter = new BufferedWriter(outputStreamWriter); String line = null; while ((line = bufferedReader.readLine()) != null) { bufferedWriter.write(line); bufferedWriter.newLine(); bufferedWriter.flush(); } } catch (Exception e) { } finally { if (null != bufferedWriter) { try { bufferedWriter.close(); } catch (IOException e) { } } if (null != bufferedReader) { try { bufferedReader.close(); } catch (IOException e) { } } } } /** * * 利用IO流拷贝本地图片 * * 原创作者 * 谷哥的小弟 * * 博客地址 * http://blog.csdn.net/lfdfhl */ private void test2() { FileInputStream fileInputStream = null; FileOutputStream fileOutputStream = null; try { fileInputStream = new FileInputStream(SDCardDir + "beauty.jpg"); fileOutputStream = new FileOutputStream(SDCardDir + "yyyy.jpg"); int len = 0; byte buffer[] = new byte[1024 * 2]; while ((len = fileInputStream.read(buffer)) != -1) { fileOutputStream.write(buffer, 0, len); fileOutputStream.flush(); } } catch (Exception e) { } finally { try { if (null != fileInputStream) { fileInputStream.close(); } if (null != fileOutputStream) { fileOutputStream.close(); } } catch (Exception e) { } } } /** * * 利用IO流加载本地图片 * * 在得到FileInputStream之后可以调用系统API获取Bitmap: * Bitmap bitmap=BitmapFactory.decodeStream(fileInputStream); * 当然,在此我们不采用该方法而是自己用IO流来读取Bitmap。 * * 嗯哼,继续说这个例子. * 在此请注意对于buffer的大小指定 * byte [] buffer=new byte[fileInputStream.available()]; * 具体大小为fileInputStream.available(). * 请注意文档的描述: * public int available() throws IOException * 返回可以不受阻塞地从此文件输入流中读取的字节数。 * 在该示例中图片保存于本地,故可不受阻塞地读取该文件 * 所以可通过fileInputStream.available()获取到文件的大小 * * 在为buffer设置完大小后再将数据读入到buffer中 * fileInputStream.read(buffer); * 再解析得到Bitmap * Bitmap bitmap = BitmapFactory.decodeByteArray(buffer, 0, buffer.length); * * 原创作者 * 谷哥的小弟 * * 博客地址 * http://blog.csdn.net/lfdfhl */ private void test3(){ FileInputStream fileInputStream=null; try { fileInputStream=new FileInputStream(SDCardDir+"beauty.jpg"); byte [] buffer=new byte[fileInputStream.available()]; fileInputStream.read(buffer); Bitmap bitmap = BitmapFactory.decodeByteArray(buffer, 0, buffer.length); mImageView.setImageBitmap(bitmap); }catch (Exception e){ }finally { try { if (null != fileInputStream) { fileInputStream.close(); } } catch (Exception e) { } } } /** * * 利用IO流加载网络图片 * * 在该示例中图片不再在本地而是在远程。 * 在这种情况下可能发生网络阻塞,企图利用 * inputStream.available()获取图片的大小是错误的; * 此时,利用该方法获取到的值远小于图片大小。 * * 那么该怎么做呢? * 可以这样: * while ((len = inputStream.read(buffer)) != -1) { * byteArrayOutputStream.write(buffer, 0, len); * } * 1 利用inputStream将数据不断地读入到buffer中,即: * while ((len = inputStream.read(buffer)) != -1) * 2 将buffer中的数据写入到ByteArrayOutputStream中,即: * byteArrayOutputStream.write(buffer, 0, len); * 3 读取完数据后将ByteArrayOutputStream中的全部字节数据保存到字节数组中 * byte[] imageData = byteArrayOutputStream.toByteArray(); * 4 解析生成Bitmap * Bitmap bitmap = BitmapFactory.decodeByteArray(imageData,0,imageData.length); * * 此示例中ByteArrayOutputStream充当了"中转站"的作用。 * 我们不能一次性从inputStream中获取到所有的数据,所以就通过 * 多次读取来获得所有的数据;每次读取后就将数据暂存于ByteArrayOutputStream. * 当完成多次读取后再将全部数据从ByteArrayOutputStream中取出 * * 原创作者 * 谷哥的小弟 * * 博客地址 * http://blog.csdn.net/lfdfhl */ private void test4(){ mAsyncTask = new DownLoaderAsyncTask(); mAsyncTask.execute("http://avatar.csdn.net/6/6/D/1_lfdfhl.jpg"); } private class DownLoaderAsyncTask extends AsyncTask<String, Integer, Bitmap> { @Override protected void onPreExecute() { super.onPreExecute(); } @Override protected Bitmap doInBackground(String... params) { InputStream inputStream = null; ByteArrayOutputStream byteArrayOutputStream = null; try { URL imageUrl = new URL(params[0]); HttpURLConnection connection = (HttpURLConnection) imageUrl.openConnection(); connection.setConnectTimeout(5000); connection.setRequestMethod("GET"); if (connection.getResponseCode() == 200) { inputStream = connection.getInputStream(); byteArrayOutputStream = new ByteArrayOutputStream(); byte[] buffer = new byte[ 1024 ]; int len; while ((len = inputStream.read(buffer)) != -1) { byteArrayOutputStream.write(buffer, 0, len); } byte[] imageData = byteArrayOutputStream.toByteArray(); Bitmap bitmap = BitmapFactory.decodeByteArray(imageData, 0, imageData.length); return bitmap; } } catch (Exception e) { } finally { try { if (null != inputStream) { inputStream.close(); } if (null != byteArrayOutputStream) { byteArrayOutputStream.close(); } } catch (Exception e) { } } return null; } @Override protected void onPostExecute(Bitmap bitmap) { super.onPostExecute(bitmap); if (null != bitmap) { mImageView.setImageBitmap(bitmap); } } } }

优秀的个人博客,低调大师

传统同步阻塞式I/O模型(BIO)

传统BIO编程 网络编程的基本模型是Client/Server模型,就是两个进程之间进行相互通信,Server端提供绑定的IP地址和监听端口,客户端通过连接操作向服务端监听的地址发起连接请求,通过三次握手建立连接,建立成功之后就可以通过Socket通信。在BIO模型开发中,ServerSocket负责绑定IP地址,启动监听端口;Socket负责发起连接操作,连接成功后双方通过输入输出流进行BIO通信。 BIO通信模式 采用BIO通信模型的Server端,通常由一个独立的Acceptor线程负责监听客户端的连接,接受到服务端的请求后为每个客户端创建一个新的线程进行链路处理,处理完成后通过输出流返回应答给客户端,线程销毁。如图 基于BIO实现的TimeServer https://github.com/chenjian44/netty_readings_note/tree/master/bio/SyncBlockingIO 弊端分析 缺乏弹性伸缩能力,当客户端访问量增加的时候,服务端的线程个数和客户端并发访问数为1:1的关系,由于线程是jvm宝贵的资源,线程膨胀之后,系统性能急剧下降,随着访问量继续增加,系统便会发生线程堆栈溢出、创建线程失败等问题,并最终导致宕机或者僵死,不能再对外提供服务。 伪异步IO编程 伪异步编程后端通过一个线程池来处理多个客户端的请求接入,形成客户端最大数M:和线程池最大数N的对应关系,M可以远大于N,通过线程池可以灵活调配线程资源,设置线程的最大值,防止由于海量线程并发接入导致线程耗尽。 伪异步通信模式 采用线程池和任务队列实现,当有新的客户端接入时,将客户端的Socket封装成一个Task(实现Runable接口)投递到后端的线程池中处理,JDK的线程池维护一个消息队列和N个活跃线程对消息队列中的任务进行处理。由于线程池可以设置消息队列的大小和最大的线程数,因此资源占用是可控的,所以更多客户端并发访问,并不会导致资源的耗尽和宕机。如图 伪异步IO实现的TimeServer https://github.com/chenjian44/netty_readings_note/tree/master/bio/PseAsyncIO 弊端分析 伪异步IO的读和写操作都是同步阻塞的,阻塞的时间取决于对方IO线程的处理速度和网络IO的传输速度。因为无法保证生产环境的网络状况和端的应用程序足够快,它的可靠性就非常差。伪异步IO只是对之前IO线程模型的一个简单优化,无法从根本上解决同步IO导致的通信线程阻塞的问题。如果通信对方返回的应答时间过长,会引起的级联故障分析: 服务端处理缓慢,返回应答消息耗费60s,平时只需要10s; 伪异步IO的线程正在读取故障服务节点的响应,由于输入流是阻塞的,它也会被同步阻塞60s; 假如所有的可用线程都被故障服务器阻塞,那后续的IO消息都将zai队列中排队; 由于线程池采用阻塞队列实现,当队列积满后,后续入队的操作将被阻塞 由于前端只有一个Acceptor线程接受客户端接入,它被阻塞在线程池的同步阻塞队列之后,新的客户端请求消息将被拒绝,客户端会发生大量的连接超时; 由于几乎所有的连接都超时,调用者会认为系统已经崩溃,无法接受新的请求消息;

资源下载

更多资源
Mario

Mario

马里奥是站在游戏界顶峰的超人气多面角色。马里奥靠吃蘑菇成长,特征是大鼻子、头戴帽子、身穿背带裤,还留着胡子。与他的双胞胎兄弟路易基一起,长年担任任天堂的招牌角色。

腾讯云软件源

腾讯云软件源

为解决软件依赖安装时官方源访问速度慢的问题,腾讯云为一些软件搭建了缓存服务。您可以通过使用腾讯云软件源站来提升依赖包的安装速度。为了方便用户自由搭建服务架构,目前腾讯云软件源站支持公网访问和内网访问。

Sublime Text

Sublime Text

Sublime Text具有漂亮的用户界面和强大的功能,例如代码缩略图,Python的插件,代码段等。还可自定义键绑定,菜单和工具栏。Sublime Text 的主要功能包括:拼写检查,书签,完整的 Python API , Goto 功能,即时项目切换,多选择,多窗口等等。Sublime Text 是一个跨平台的编辑器,同时支持Windows、Linux、Mac OS X等操作系统。

WebStorm

WebStorm

WebStorm 是jetbrains公司旗下一款JavaScript 开发工具。目前已经被广大中国JS开发者誉为“Web前端开发神器”、“最强大的HTML5编辑器”、“最智能的JavaScript IDE”等。与IntelliJ IDEA同源,继承了IntelliJ IDEA强大的JS部分的功能。

用户登录
用户注册