DELPHI下多线程编程的几个思维误区(QDAC)
有几个网友私下问我一些有关线程的事情。过节写个东西上来大家交流。
思维误区1,自己新建的THREAD是线程,自己的主程序不是线程. 很多人在多线程编程没有把主线程也当作线程。其实主线程也是线程。看起来是废话,这个话确实很重要,这个就意味着,在DELPHI中,不光你开的线程,还有你的主线程所有的内存分配也是串的,进锁排队的。主线程和线程的区别
A.一般来说主线程的优先级高了点。(当然你也可以自己设置)
B.主线程在WIN下是处理APPLICATION的消息。
其他基本与你自建线程无区别。
所以这一点还可以点破小白问题,比如主线程不能进锁。其实主线程也要进锁的。关键是主线程不能挂起死等。挂起死等就用户界面卡了或者假死了。所以要进代码一边等,一边切换到其他任务。
思维误区2.线程和面向对象。
C的时候写线程反而很简单。因为C不是面向对象的。 撸代码的时候非常清楚什么在线程,什么在主线程,因为撸代码思维和机器表现一致。但是DELPHI是面向对象的。经常老会问自己类似这样的问题:这个对象在主线程还是在线程。这个OO中毒太深了,这个问题我也问过。其实DELPHI也不是绝对的面向对象,只是面向对象的封装而已,其本质还是流式代码跟C没区别,也就是跟OO没有半毛关系。
那问 这个对象在线程跑还是在主线程跑? 我只能说,所有对象都在内存,至于你哪里跑要看你的线程走了多少代码。比如
TAAAA= CLASS;
Public
procedure A;
procedure B;
procedure C;
(假设Procedure A,B,C相互没有资源冲突和相互调用)
APP代码你调用了Procedure A. 建了一个线程,线程调用Procedure B, 线程结束。
主线程跑了Procedure A, 自己建的线程跑了Procedure B. 但是他们都属于类TAAAA。
所以思维要改回来,线程跟面向对象没有半毛钱关系。不要用面向对象的思维去设计你的线程。这样你就知道你的锁该放在哪里了。
思维误区3. 锁和无锁
很多编程书里把锁讲成如厕(群里我把这个比喻成偷人,因为如厕不够污,记不住,偷人够污,容易记住。)。一个人进了厕所,其他人在门外面等着。锁就是门,人就是线程。这样的设置就是竞争机制,厕所少,人多啊。假如没有竞争机制,那当然不要锁了,每人发一个厕所,人人都幸福啊。编程中,比如固定的配置数据,你跑线程的时候每个线程配一个复本。那就不要锁了。
锁是影响你的程序效率的。犹如这边要尿急了,厕所里的人还没有出来,心里OS,TMD上个厕所真麻烦。 你要降低锁在程序里的开销。无非几个有因素:
A.锁本身的开销。(好比:上厕所里面的人出来,外面的人进去本身要时间的,这个就是锁的开销–我是乱比喻了,其实不是这样的,但是本质差不多,这样讲便于理解)。所以操作系统提供很多锁的资源和方式,所谓原子锁。其实也是锁。
B,线程等太久。
犹如上厕所等太久,多费劲啊。要解决也就2个方面,
B1,里面的人蹲太长时间了,憋死了。所以你要尽量使你的LOCK里面的任务减少。防止蹲太久.
B2,等的人太多。。排队排到大街上了。所以你要规划好你的资源。让资源分片—这个做法好比设了多个厕所。解决方案还有一个就是线程池。就是减少人。这个用如厕的比喻估计更加污。还是表达出来便于理解。“犹如,设几个人把所有人的大便都拉了。”
很多事,道理真的就这么简单。设计线程模型的时候别想多了就行。难就难在设计的时候自己容易想多,想着想着就无解了,那是自己给自己的坑啊。
http://blog.qdac.cc/?p=4564
DELPHI下多线程编程的几个思维误区(QDAC)的更多相关文章
- Windows环境下多线程编程原理与应用读书笔记(1)————基本概念
自从学了操作系统知识后,我就对多线程比较感兴趣,总想让自己写一些有关多线程的程序代码,但一直以来,发现自己都没怎么好好的去全面学习这方面的知识,仅仅是完成了操作系统课程上的小程序,对多线程的理解也不是 ...
- Delphi 实现多线程编程的线程类 TThread
http://blog.csdn.net/henreash/article/details/3183119 Delphi中有一个线程类TThread是用来实现多线程编程的,这个绝大多数Delphi书藉 ...
- delphi之多线程编程(尚未学习)
本文的内容取自网络,并重新加以整理,在此留存仅仅是方便自己学习和查阅.所有代码均亲自测试 delphi7下测试有效.图片均为自己制作. 多线程应该是编程工作者的基础技能, 但这个基础我从来没学过,所以 ...
- Linux下多线程编程
一.为什么要引入线程? 使用多线程的理由之一是和进程相比,它是一种非常"节俭"的多任务操作方式.在Linux系统下,启动一个新的进程必须分配给它独立的地址空间,建立众多的数据表来维 ...
- Windows下多线程编程(一)
前言 熟练掌握Windows下的多线程编程,能够让我们编写出更规范多线程代码,避免不要的异常.Windows下的多线程编程非常复杂,但是了解一些常用的特性,已经能够满足我们普通多线程对性能及其他要求. ...
- Linux下多线程编程-信号量
今天来谈谈线程的同步--信号量. 首先来看看一些概念性的东西: 如进程.线程同步,可理解为进程或线程A和B一块配合,A执行到一定程度时要依靠B的某个结果,于是停下来,示意B运行:B依言执行,再将结果给 ...
- Linux下多线程编程遇到的一些问题
今天在学习了Linux的多线程编程的基础的知识点.于是就试着做了一个简单的Demo.本以为会得到预期的结果.不成想却遇到了意想不到的问题. 代码展示 我的C 代码很简单,就是一个简单的示例程序,如下: ...
- delphi之多线程编程
本文的内容取自网络,并重新加以整理,在此留存仅仅是方便自己学习和查阅.所有代码均亲自测试 delphi7下测试有效.图片均为自己制作. 多线程应该是编程工作者的基础技能, 但这个基础我从来没学过,所以 ...
- Delphi下DLL编程知识(转)
一. DLL和系统变量 在 System 单元声明的变量中,有几个对DLL编程有特殊影响.IsLibrary 可以检测代码是执行在应用程序中还是执行在DLL中,在应用程序中 IsLibrar ...
随机推荐
- [Git] How to rename your remote branch
Rename your local foo branch with bar: git branch -m foo bar Remember this will add the new branch w ...
- php实现 句子逆序(需求才是最好的老师)
php实现 句子逆序(需求才是最好的老师) 一.总结 一句话总结:需求才是最好的老师. 1.str_split()和explode()的区别? explode — 使用一个字符串分割另一个字符串 3 ...
- [Vue] Use Vue.js Component Computed Properties
You can add computed properties to a component to calculate a property on the fly. The benefit of th ...
- 基于 Android NDK 的学习之旅-----数据传输(引用数据类型)
接着上篇文章继续讲.主要关于引用类型的数据传输,本文将介绍字符串传输和自定义对象的传输. 1.主要流程 1. String 字符串传输 a) 上层定义一个native的方法,需要一个 ...
- Angular.js回想+学习笔记(1)【ng-app和ng-model】
Angular.js中index.html简单结构: <!doctype html> <html ng-app> <head> <script src=&qu ...
- 小强的HTML5移动开发之路(37)——jqMobi快速入门
在<小强的HTML5移动开发之路(33)-- jqMobi基础>中我们了解了什么是jqMobi,并从官方下载了jqMobi开发包,下载后解压目录如下: 拷贝上面的/css目录./plugi ...
- 【bzoj2809】派遣 (左偏树)
传送门 题目分析 每个节点都是一颗(大根堆)左偏树,先按bfs序存入数组,然后倒着从底层开始:如果当前节点的子树sum > m 那么就把根节点删去,然后统计更新答案,并将这棵树和父节点合并. c ...
- mysql 数据库 添加查询 修改 删除
cmd 命令行模式操作数据库 添加查询 修改 删除 ( 表 字段 数据) 一 查看数据库.表.数据字段.数据 1 首先配置环境变量 进入mysql 或者通过一键集成工具 打开mysql命令行 ...
- 【22.48%】【codeforces 689D】Friends and Subsequences
time limit per test2 seconds memory limit per test512 megabytes inputstandard input outputstandard o ...
- Sleep(0)的妙用
在线程中,调用sleep(0)可以释放cpu时间,让线程马上重新回到就绪队列而非等待队列,sleep(0)释放当前线程所剩余的时间片(如果有剩余的话),这样可以让操作系统切换其他线程来执行,提升效率. ...