备忘录--关于线程和IO知识
因为自己还在出差中,没时间深入学习,最近工作里又有对一些技术的思考,所以这里记录下来,等回去有时间可以按照这个思路进行学习,这里主要起到备忘的作用。
1.线程难学难在我们没有理解操作系统里的线程设计机制,最近我学习了两个关于线程设计的原理,一个是分时系统里线程是按照时间片进行执行的,可是多线程里大部分线程都不能在一个时间片里全部执行完毕,那么时间片就要轮换,这里其实还有个问题就是存放线程的队列是如何设计的,轮换线程时候它有何种算法。当操作系统是单核时候也许理解这些很容易,那么当操作系统是多核时候,问题来了,操作系统又是如何在多核环境下调度线程的呢?而且现在的服务器基本都是多核的,这个问题需要好好研究下。
2.程序执行都是内存和CPU共同作用的结果,线程安全问题就是一个线程执行完时间片之后,其实它并没有结束,而是休眠起来等待下一次的调度,这个时候内存的数据是被处理一部分或者说这些数据还没算完,如果说另外一个线程再去操作了这些数据就有可能导致内存数据发生变化,从而导致最终结果出错,这就是线程安全问题,所以一般线程安全问题的解决方案就是给数据上锁,这个锁只会被一个线程拥有,那么当时间片轮换时候,其他线程碰到这个加锁的数据就会停止操作。所以在java里锁都是设置在Object对象上,也就是锁都是加在数据上。现在的jdk里对数据加锁更加细粒度话,这个细粒度是何种原理设计的,这个需要好好研究。
3.原子操作就是指不会被时间片打断的操作,换个说法就是CPU在一个时间片下一定要执行完毕的操作,其本质就是CPU里一个不可分割的算子,基础数据类型的操作往往都是原子操作例如int的加减乘除,但是java现在把很多复杂对象也做成这样了,这个问题就需要我回去细细分析,这些对象的原子类到底是CPU拥有的复杂算法了?还是讲锁直接封装在了对象上了。
4.多核编程里有一点是可以肯定的,那就是多个核心的CPU是可以并行处理的,所以多核CPU才有真正的并行操作,但是问题来了,CPU可以多核,内存可不是多核啊,那么这个时候给内存数据加锁,以及原子操作会有何种变化。单核系统的并行操作是一个伪并行,但是多核的并行有可能是真并行,那么这个时候真正并行的内存访问同一份数据就会有问题,这个细节我现在实在不清楚,需要抽时间好好研究下。此外我们编写程序有的对象是专门存储数据,其实算法例如循环,分支也是会被存储在内存里,告诉CPU该如何计算,那么这些不同类型的存储数据到底在内存里该如何分配了,它们到底是何种类型,这个就需要我进一步研究jvm的内存模型,自己能提出这个问题很重要,我能感受到这个问题也就说明我不再是糊里糊涂的去看jvm的相关知识了。
5.听朋友说一些高级的CPU还有超线程技术,可以模拟单核真并发,这个也需要研究下。
6.关于线程调度机制,单核下或许我并不想深究这个问题,但是多核下的调度呢?如果我们不能理解多核调度,那么写出优秀的多核多线程会有什么隐患呢?
7.关于IO的问题,IO,内存和CPU这三者的效率相比,IO实在慢的太多,当程序需要很高效率,同时又是IO密集型操作,那么处理IO,内存和CPU关系就会显得尤为重要,我最近发现IO难学其实和线程难学是一直的,要理解深入IO就的深入了解操作系统的IO操作原理,例如IO多路复用,selector,poll,epoll,我最近想抽点时间先查阅下相关资料。
以上都是备忘之需。最后聊下现在心情,坏心情:实在讨厌出差,特别是到现在还不知道啥时候能回家的出差,每次都觉得下星期能回,现在感觉估计11月都回不了了,等以后有机会一定找个不出差或者少出差的工作。
好心情:每天都要看看新闻,希望武汉越来越好,最近发现武汉房子买的越来越好,这就说明很多外来人口来武汉,我想如果武汉能保持这样势头,武汉的未来一定不错,武汉不错,我这样的大头百姓也会有更多机会了。