Thursday, December 11, 2008

MA; 移动平均线

移动平均线指标使用入门

移动平均线的计算方法就是连续若干天的收盘价的算术平均。天数就是的参数。例如,参数为10的移动平均线就是连续10日的收盘价的算术平均价格,记号为MA(10)。同理,还有5日线、30日线等概念。

移动平均线的特点:

移动平均线的最基本的作用是消除偶然因素的影响,另外还稍微有一点平均成本价格的含义。它具有以下几个特点。

追踪趋势。移动平均线能够表示价格的趋势方向,并追随这个趋势,不轻易放弃。如果从价格的图表中能够找出上升或下降趋势线,那么,移动平均线的曲线将保持与趋势线方向一致,能消除中途价格在这个过程中出现的起伏。原始数据的价格图表不具备这个保持追踪趋势的特性。

滞后性。在价格原有趋势发生反转时,由于追踪趋势的特性,移动平均线的行动往往过于迟缓,调头速度落后于大趋势。这是移动平均线的一个极大的弱点。等移动平均线发出趋势反转信号时,价格调头的深度已经很大了。

稳定性。由移动平均线的计算就可知道,要比较大地改变它的数值,无论是向上还是向下,都比较困难,必须是当天的价格有很大的变动。因为MA的变动不是一天的变动,而是几天的变动,一天的大变动被几天一分摊,变动就会变小而显不出来。这种稳定性有优点,也有缺点,在应用时应多加注意,掌握好分寸。

助涨助跌性。当价格突破了移动平均线时,无论是向上突破还是向下突破,价格有继续向突破方面再走一程的愿望,这就是移动平均线的助涨助跌性。

支撑线和压力线的特性。由于移动平均线的上述4个特性,使得它在价格走势中起支撑线和压力线的作用。移动平均线的被突破,实际上是支撑线和压力线的被突破。

移动平均线的参数的作用就是加强移动平均线上述几方面的特性。参数选择得越大,上述的特性就越大。比如,突破5日线和突破10日线的助涨助涨的力度完全不同,10日线比5日线的力度大,改过来较难一些。

使用移动平均线通常是对不同的参数同时使用,而不是仅用一个。按个人的不同,参数的选择上有些差别,但都包括长期、中期和短期三类。长、中、短是相对的,可以自己确定。

Wednesday, December 10, 2008

Email accounts

qiang.ma@ymail.com
qiangma@rocketmail.com

feng.zhang@rocketmail.com

选股指标摘要

1. 价托,量托

多空变成多头排列,这个过程中会出现一个三角形,形成一种所谓的价格和量的支撑

2.

查外网IP地址

去 www.hostip.info 显示你的外网IP

Tuesday, December 2, 2008

Remove Malware for Windows

Malwarebytes' Anti-Malware

http://www.malwarebytes.org/

ccleaner.com

http://www.ccleaner.com/

Monday, December 1, 2008

耐得住寂寞更易成功

传说中,西西里岛附近海域有一座塞壬岛,长着鹰的翅膀的塞壬女妖日日夜夜唱着动人的魔歌引 诱过往的船只。在古希腊神话中,特洛伊战争的英雄奥得修斯曾路过塞壬女妖居住的海岛。之前早就听说过女妖善于用美妙的歌声勾人魂魄,而登陆的人总是要死 亡。奥得修斯嘱咐同伴们用腊封住耳朵,免得他们被女妖的歌声所诱惑,而他自己却没有塞住耳朵,他想听听女妖的声音到底有多美。为了防止意以外发生,他让同 伴们把自己绑在桅杆上,并告诉他们千万不要在中途给他松绑,而且他越是央求,他们越要把他绑得更紧。

  果然,船行到中途时,奥得修斯看 到几个衣着华丽的美女翩翩而来,她们声音如莺歌燕啼,婉转跌宕,动人心弦。听着这美妙的歌声,奥得修斯心中顿时燃起熊熊烈火,他急于奔向她们,大声喊着让 同伴们放他下来。但同伴们根本听不见他在说什么,他们仍然在奋力向前划船。有一位叫欧律罗科斯的同伴看到了他的挣扎,知道他此刻正在遭受着诱惑的煎熬,于 是走上前,把他绑得更紧。就这样,他们终于顺利通过了女妖居住的海岛。

  这是一个神话故事,带有强烈的虚构和夸张成分。但是现实中类似的事情却比比皆是。

  朋友燕是一家会计师事务所的员工。春节,老同学聚会,她也来了,看看同学们个个体态灵珑,再看看自己发福的身材,不禁自惭形秽,于是下决心不再吃那些高热量的食品了,要多吃蔬菜和水果。

  近日,我们又在一起吃饭,她一见到有炸鸡,口水都流出来了,一位好友提醒她,“你不是要减肥吗?”燕嘿嘿一笑:“不让我吃,还不如杀了我!”于是不由自主地就去享用这些美味了。结果可想而知。

  发展心理学的“糖果实验”:那些忍住诱惑的孩子,成年后在事业上更易成功。

   60年代,美国心理学家瓦特·米伽尔给一些4岁小孩子每人一颗非常好吃的软糖,同时告诉孩子们可以吃糖,如果马上吃,只能吃一颗;如果等20分钟,则能 吃两颗。有些孩子急不可待,马上把糖吃掉了。另一些孩子却能等待对他们来说是无尽期的20分钟,为了使自己耐住性子,他们闭上眼睛不看糖,或头枕双臂、自 言自语、唱歌,有的甚至睡着了,他们终于吃到了两颗糖。

  这个实验后来一直继续了下去,那些在他们几岁时就能等待吃两颗糖的孩子,到了青少年时期仍能等待,而不急于求成;而那些急不可待,只吃了一颗糖的孩子,在青少年时期更容易有固执、优柔寡断和压抑等个性表现。

   当这些孩子长到上中学时,就会表现出某些明显的差异。对这些孩子的父母及教师的一次调查表明,那些在4岁时能以坚忍换得第二颗软糖的孩子常成为适应性较 强,冒险精神较强,比较受人喜欢,比较自信,比较独立的少年;而那些在早年已经不起软糖诱惑的孩子则更可能成为孤僻、易受挫、固执的少年,他们往往屈从于 压力并逃避挑战。对这些孩子分两级进行学术能力倾向测试的结果表明,那些在软糖实验中坚持时间较长的孩子的平均得分高达210分。

  研究人员在十几年以后再考察当年那些孩子现在的表现,研究发现,那些能够为获得更多的软糖而等待得更久的孩子要比那些缺乏耐心的孩子更容易获得成功,他们的学习成绩要相对好一些。在后来的几十年的跟踪观察中,发现有耐心的孩子在事业上的表现也较为出色。

  哈佛大学心理学家丹尼尔·戈尔曼:自律对一生的成功都很重要!

  哈佛大学心理学家丹尼尔·戈尔曼的《情商》一书,把情绪智力(也称情商,EQ)定义为“能认识自己和他人的感觉,自我激励,以及很好地控制自己在人际交往中的情绪的能力。”这一理念很快跨过大西洋,成为英国工业、教育和公共生活领域的主流思潮。

   一些国际大公司也将情商测试作为选用人才的依据。情商分为5种情绪能力和社会能力:自知、移情、自律、自强和社交技巧。自知,意味着知道自己当前的感 受。因为我们整天都忙忙碌碌,所以就无暇顾及反省和自知。一个人的自我形象与其在他人眼中的形象越一致,他的人际关系就越成功。情商的第二个组成部分(移 情),能培养我们的同情心和无私精神,并能带来合作。情商的第三部分是控制自己情绪的能力。情商高的人能更好地从人生的挫折和低潮中恢复过来。第四部分是 自强。自强的人能够很好地控制情绪,不靠冲击或刺激就能采取行动。最后,社交技巧指的是通过与他人友好的交流来掌握人际关系的能力。情绪智力溯源一个高智 商的人,完全可以与一个低智商但有着高水平交往技巧的人很好地合作。戈尔曼将高情商与成功联系起来,并以上面提到的“糖果实验”的例子来阐明控制冲动的重 要性。“糖果实验”说明了自律对一生成功的重要性。

  某种诱惑能满足你当前的需要,但却会妨碍达到更大的成功或长久的幸福。

  无论是神话,还是现实,成年人还是孩子,它们都反映着同样的道理:克制欲望、抵抗诱惑是多么困难,古往今来,“引无数英雄竞折腰”。想一想不时出现在电视镜头中的那些落马的腐败官员,曾经何等显赫风光,接受审查时又是如何满脸失落沮丧。

   一位作家说:“其实人与人都很相似的,不同就那么一点点。”这一点点,在相当程度上,就是一种自我克制的能力。正是由于对自我的欲念的调控,才显现出人 性的高贵与光辉。进行“糖果实验”的米伽尔同时发明了一个冗长的词汇:“目标导向的自发式延迟满足”。他十分强调自我调节情绪的意义,认为只有克制冲动才 能有效达成某种目标。

  所谓的目标是多方面的。作为普通人,我们不可能像高官那样时常面对金钱、权力与美色,但在我们的生活中也经常存 在着各种各样或大或小的诱惑。比如,你明明知道吸烟对身体不好,但却因为吸烟的快感放纵自己继续吸烟;明明知道努力学习有利于今后的成功,但却难以放弃现 在轻松自在的生活而投入紧张的学习中。奥德修斯塞住耳朵,束缚手脚,战胜了海上女妖魔法的诱惑,并历经种种风险,终于回到朝思暮想的家园。20世纪60年 代的美国,物质条件远不及现在丰富,为了得到心爱的美味糖果,四岁的小孩子是如何在煎熬中度过20分钟的?

  在一粒芝麻与一颗西瓜之间,你一定明白什么是明智的选择。如果某种诱惑能满足你当前的需要,但却会妨碍达到更大的成功或长久的幸福。那就请你屏神静气,站稳立场,耐得住寂寞。一个人是这样,一个企业,一个社会也是这样。

Friday, November 21, 2008

The Top 3 Reasons to Buy VMware Today

Let me tell you a story about innovation, superior growth, and killer sharks with laser-beams on their frickin' heads. And along the way, you'll find the best tech stock I know -- and it's so cheap, it's ridiculous.

Virtual machines are sweeping through data centers the world over, simplifying hardware setups and bringing down power consumption and management costs in their wake. VMware (NYSE: VMW) started this sea change years ago, and remains virtually unchallenged at the top of the fledgling industry's heap.

But the stock gets about as much respect as Rodney Dangerfield's dog. In the last six months, VMware's shares have lost around a stunning 70% of their value, underperforming not only the flagging market as a whole but also most of its rivals, large and small:

Company

6-Month Price Change

Trailing P/E Ratio

CAPS Rating

VMware

(71%)

30

***

Microsoft (Nasdaq: MSFT)

(35%)

9

***

Citrix Systems (Nasdaq: CTXS)

(39%)

22

****

Oracle (Nasdaq: ORCL)

(28%)

14

****

Sun Microsystems (Nasdaq: JAVA)

(75%)

N/A

**

Yahoo! Finance and Motley Fool CAPS as close of Nov. 19, 2008.

While several of these companies look attractive today, none can match the buying opportunity we see in VMware right now. Let me show you three things that Mr. Market seems to have forgotten when it comes to VMware's value:

1. Mr. Market forgot about growth
The proper price for any stock must take future growth into account. VMware is priced as if virtualization software already ran out of room to grow. Hold that thought -- we'll get back there in a second.

With an estimated PE-to-growth ratio of around 0.70, VMware is the kind of stock that value investors drool over. The stock needs to take around a 40% leap to grow into a reasonable ratio of 1. This is very cheap in comparison to other virtualization players.

2. Mr. Market forgot about moats
VMware has built a moat around its business model, miles wide and filled with angry mutant sharks. Having essentially created this market on its own, VMware remains far ahead of closest competitor Microsoft's virtual server and hypervisor technology -- and keeps adding business-worthy features at an accelerated pace.

And just in case a biggie like Mr. Softy or Oracle tries an all-out marketing assault to muscle its way into VMware's castle, sugar daddy EMC (NYSE: EMC) holds over 80% of VMware's shares and can flex its own marketing muscle in response. Granted, EMC is much smaller than Microsoft and Oracle, but it's still a multibillion dollar company and can provide some protection. Sometimes it's nice to have big-time corporate backing.

3. Mr. Market forgot about market size
Back to the size of this market: Right now, VMware's trailing sales stop at a pesky $1.8 billion a year, while Citrix and Microsoft have much lower market share in virtualization.

Let's pretend that virtualization software was free (some of it is, some isn't) and always will be. In that alternate reality, VMware's chief source of income would be training and support services for administrators of its virtual machines. That means taking market share from the hardware guys as IT management becomes more involved with hypervisors and virtual hardware -- and less with supporting a plethora of IBM (NYSE: IBM) machines. One large box from Big Blue can run dozens of virtual machines. That means less IBM support and more VMware support for every one of those data-centers-in-a-box.

IBM alone made billions of revenue in support services last year, and that doesn't even account for other hardware makers or stand-alone support specialists. According to IDC, the combined annual market for server support reached somewhat higher than $10 billion in 2007. I think it is likely this will be higher for 2008. So if virtualization takes a fraction of those sales, the undisputed leader of that market should see tremendous growth in its own right.

There's much more to this exciting growth story: eco-friendly features at a time of green thinking, enthusiastic support from the chip makers, the whole cloud computing trend, and much more. To top it off, management just renewed its view of 42% revenue growth or better in 2008 despite the wacky economy. Imagine what this stock could do in a good year.

Buy low (that would be right now) and sell high (or possibly never). And that's how you get rich in the stock market.

Thursday, November 20, 2008

选股指标

市盈率:P/E price-to-earnings

市盈率是某种股票每股市价与每股盈利的比率。(市盈率=普通股每股市场价格÷普通股每年每股盈利)上式中的分子是当前的每股市价,分母可用 最近一年盈利,也可用未来一年或几年的预测盈利。市盈率是估计普通股价值的最基本、最重要的指标之一。一般认为该比率保持在20-30之间是正常的,过小 说明股价低,风险小,值得购买;过大则说明股价高,风险大,购买时应谨慎。但高市盈率股票多为热门股,低市盈率股票可能为冷门股。



Monday, November 3, 2008

EXCEL 单元格操作

相对位置 v.s. 绝对位置

默认情况下是用相对位置,要改变成绝对引用(会出现美元符号),选中公式中相应部分按F4。

快速插入多行
1. 右键先插入一行,然后按F4(重复上一次操作)多次。
2. 选择多行,然后右键选择插入

数据有效性
data -> validation->Allow list

批量录入
1. 选定区域
2. F5, 定位对话框
3. 输入
4. ctrl+enter

批量缩放
1. 复制
2. 选定区域,右键选择性粘贴
3. 选择相应公式

alt + 178 平光
alt + 179 立方
alt + 41409 钩
alt + 41420 叉

Friday, October 31, 2008

system call example (1)

参考文献:

Chapter 4, Linux kernel development second edition

深入LINUX内核:为你的LINUX增加一条系统调用

  充分利用LINUX开放源码的特性,我们可以轻易地对它进行修改,使我们能够随心所欲驾驭LINUX,完成一个真正属于自己的操作系统,这种感觉使无与伦比的,下面通过为LINUX增加一个系统调用来展示LINUX作为一个开放源码操作系统的强大魅力。
  首先,让我们简单地分析一下LINUX中与系统调用的相关的部分:
  LINUX的系统调用的总控程序是system_call,它是LINUX系统中所有系统调用的总入口,这个system_call是作为一个中断服务程序挂在中断0x80上,系统初始化时通过void init trap_init(void)调用一个宏set_system_ gate(SYSCALL_VERCTOR,&system_call)来对IDT表进行初始化,在0x80对应的中断描述符处填入system_call函数的地址,其中宏SYSCALL_VERCTOR就是0x80
  当发生一条系统调用时,由中断总控程序保存处理机状态,检查调用参数的合法性,然后根据系统调用向量在sys_call_table中找到相应的系统服务例程的地址,然后执行该服务例程,完成后恢复中断总控程序所保存的处理机状态,返回用户程序。
  系统服务例程一般定义于kernel/sys.c中,系统调用向量定义在include/asm-386/unistd.h中,而sys_call _table表则定义在arch/i386/kernel/entry.S文件里。
  现在我们知道增加一条系统调用我们首先要添加服务例程实现代码,然后在进行对应向量的申明,最后当然还要在sys_call_table表中增加一项以指明服务例程的入口地址。
  OK,有了以上简单的分析,现在我们可以开始进行源码的修改,假设我们需要添加一条系统调用计算两个整数的平方和,系统调用名为add2,我们需要修改三个文件:kernel/sys.c , arch/i386/kernel/entry.S include/asm-386/unistd.h
  1、修改kernel/sys.c ,增加服务例程代码:
  asmlinkage int sys_add2(int a , int b)
    
{
      
int c=0;
      
c=a*a+b*b;
      
return c;
    
}
  2、修改include/asm-386/unistd.h ,对我们刚才增加的系统调用申明向量,以使用户或系统进程能够找到这条系统调用,修改后文件如下所示:

  .... .....
  #define _NR_sendfile  
187
  #define _NR_getpmsg   
188
  #define _NR_putmsg    
189
  #define _NR_vfork    
190
  #define _NR_add2     191   /* 这是我们添加的部分,191即向量
*/
  3、修改include/asm-386/unistd.h , 将服务函数入口地址加入 sys_call_table,首先找到这么一段:

  .... .....
  
.long SYMBOL_NAME(sys_sendfile)
  
.long SYMBOL_NAME(sys_ni_syscall) /* streams 1 */
  
.long SYMBOL_NAME(sys_ni_syscall) /* streams 2 */
  
.long SYMBOL_NAME(sys_vfork) /*190 */
  
.rept NR_syscalls-190
  修改为如下:

  .... .....
  
.long SYMBOL_NAME(sys_sendfile)
  
.long SYMBOL_NAME(sys_ni_syscall) /* streams 1 */
  
.long SYMBOL_NAME(sys_ni_syscall) /* streams 2 */
  
.long SYMBOL_NAME(sys_vfork) /*190 */
  .long SYMBOL_NAME(sys_add2) <=我们的系统调用

  .rept NR_syscalls-191 <=190改为191
  
OK,
大功告成,现在只需要重新编译你的LINUX内核,然后你的LINUX就有了一条新的系统调用int add2(int a, int b)

urg

Monday, October 27, 2008

Excel 画X, Y

先选定Y轴的数据,然后,向导作图.选择"自定义"中的"平滑直线图",生成 后,选择下面的"下一步",在新对话框里,点选顶上的"系列",再点击下面的"分类X轴标志"框最右边的那个记号,这时,大框消失,出现一个小框,你再在 表中选择X轴数据区域.接着,点一下那个小对话框最右边的标志.这样就回到上一步的对话框了.你确定.OK.

Saturday, October 25, 2008

GNU GRUB

Rebuild the kernel

1. Download the kernel from http://www.kernel.org
tar xvzf linux-x.y.z.tar.gz
Read the READ me file at the root directory.

2. make menuconfig

3. make modules_install

4. make install

5. modify grub configuration file /boot/grub/menu.lst if it is not modified by step 4.

6. reboot and select the new kernel

title SUSE Linux Enterprise Desktop 10
root (hd0,4)
kernel /boot/vmlinuz root=/dev/sda5
initrd /boot/initrd

The initial ramdisk, or initrd is a temporary file system commonly used by the Linux kernel during boot. The initrd is typically used for making preparations before the real root file system can be mounted.

Friday, October 24, 2008

Mouth ulcer or Canker sore 口腔溃疡

意可贴等价物:(CVS有的卖)

Canker Cover Patches Mint Flavor

8-Hour canker sore treatment. Immediate pain relief. Protects mouth sores from irritation. Keeps breath fresh. Breakthrough technology. Clinically proven. Canker Cover lasts 8-12 hours before dissolving, releasing safe, natural and effective nutrients for rapid results and soothing pain relief. In most cases, a single patch is all that's needed. Oral pain reliever. For the relief of pain associated with canker sores or minor irritation or injury of the mouth and gums.











Qty:




Friday, October 17, 2008

中长期规划---螺旋式上升方式修改完善职业之路zz

一、中长期职业发展的自我准备
1、心态上随时做好准备 机会是给有准备的人的------“有准备”是你在做准备的过程中让“别人”认为你“有准备”!别人是包括你现在的老板和别的老板,以及你身边的人!他们对你的赏识程度决定了你的机会
2、专注于自己的优势 70%专注与长处,25%专注于学新事物,5%专注于避免短处
3、不断修正自己的技术方向,扩大自己的知识与能力的金字塔 增强自己的核心竞争力,但尽量别改变太多太快(今天做手机、明天做电视、后天做空调,这样很乱的,大大不利)
4、积极争取机会 柳传志说,杨元庆就是“哭着喊着要进步”,实际上,就是争取自己的机会;当然,这种强烈的进步欲望,也是领导看重的地方。每一步都走在前面,积累多了,你就有了比其他人更多的机会了。要积极争取如下机会:
a、做新项目的机会  
b、到新部门的机会  
c、带新人的机会 如果公司不安排带,那就自己主动去帮助新人,做半个师傅。
d、管理项目的机会  
e、管理团队的机会(卡位非常非常重要) 
5、做多揽活干的傻子 与工作相关的事情,没人做就主动去做;别人没干好就主动帮他们干好 要乐意去干工作职责范围以外的事情
6、使自己变得不可替代 最重要的就是,别人做到的你要做得更加好,别人做不到的你就要做到,要不断超越老板的期望!才能赢得老板或者别的老板的信任,才能得到更多的机会与回报!
6、 关注技术、公司及相关行业的发展,达到对技术、技术发展趋势、团队管理、行业情况与发展趋势等能吹能侃的地步

二、中长期规划时间表:
0-2年内  多干蓝领的工作,多学习多积累技术经验
2-4年内  多看技术发展趋势方面文章,多交与本职岗位相关的朋友
4-6年内  多看技术发展趋势与行业发展趋势文章,多交与本部门业务相关的朋友
6年以后   多看管理书籍,多了解行业发展趋势,多交与本行业相关的朋友
8年后--  多与产业链的朋友及资本相关的朋友交流

三、需要纠正的几个观念:
1、不是每个工程师都适合做管理的 走技术路必然会和走管理路分开
2、不是人人都可以做市场做销售的 性格、亲和力、知识结构等影响很大
3、不是人人都可以做老板开公司的 小老板辛苦程度高,其实还不如高级白领滋润(特别是IC,最适合工程师打工的)

四、螺旋式上升方式修改完善职业之路 大公司与小公司循环,职位与薪水自然跟着循环,职业生涯平台自然跟着上

Wednesday, October 15, 2008

美国海归经历:国内外生活真实比较zz

chipsmith 发表于 2008-10-15 17:32:00

各位都是在美国呆久了,完全按照美国的思考方式来套中国,那自然是国内年薪和美国比太低了。我在美国时也和各位想法差不多,那时候在美国一年下来税前也有8万多(我在的地方在美国算中等偏上的消费水平,房租one bed room一个月$800)。回国的offer给了三十几万,算了半天才下决心。等到了国内发现完全不是那么回事。一来国内的税低,年收入50万以下真正交的税在22%左右。此外还有住房公积金,一般是10%,也就是说你工资的10%放在公积金里,剩下的90%才交税,公司另外在match 10%的工资,这比美国的401k可强多了。通常年末还有10%的奖金,和美国同样的stock option。所以算下来实际拿到手里的税后也是三十几万。而在加州这种地方一年的联邦税和州税加起来怎么也在30%以上,大打折扣。当然在国内时间久了,你还会有做个生意等其他赚钱的法子。此外国内的外企里有各种补助,比如手机费报销(我现在的公司一个月最多1000元,足够了),午饭(500元)等等。国内实实在在做research的很少,大多都要和客户打交道,这样出去吃饭打车的开销都可以报销。我现在也就是租个房子花钱,2000每月在北京不比美国的apartment差,上网水电杂费一月四百,其余还不是衣服鞋子追追女孩。兄弟我在美国作过几年IT咨询的,美国东南西北都跑过,要说看到的中国人个个都挺省的,大多数情况下自己做饭,也没见租多好的房子,要攒个四五年才出个首付,连看个电影都很少。美国值得一提的地方就是环境,还有城郊的一个single house。在国内可以说是五光十色。我觉得回不回去看个人性格和背景,你要是做research或编程序的,性格内向,在国内只会吃亏,不会有什么太大发展。要是你性格外向,想做市场或者销售,开公司,那赶快收拾收拾回家了吧,熬着实在难受。兄弟我说的可能有点不清楚,我在美国工作了几年后又念了个MBA才回去的,所以你说我是学生刚回去也可以。我在美国是做IT咨询的,其实就是系统集成和架构设计,再管管和印度方面的外包服务,技术含量不如编程序的高,不过和各种各样的客户打交道,挺长见识的。在美国我就是一普通作技术的,工资8万在IT行业里不算高,相信在美国做过的都清楚,就是由两三年工作经验人的平均数,真没什么好吹的,只是供大家参考。至于税,我从来都是用TurboTax之类的软件,不大会用exemption,加上加州的州税高,确实就是30%那个数。当然我也交401K(我那会好像是11000每年),不过剩下的还是有30%交给Uncle Sam了。俺在美国就买过本公司的股票,因为有15% discount,不过还是赔了点,买股票赚钱真的不容易。我现在从TOP 20 B-School出来,也不认为以个人的精力和掌握的信息炒股能真赚到大钱,当然管个基金除外。至于在国内的工资水平,有过几年美国经验的,只要不是人太死板纯搞技术,三十几万在IT行业的外企真不算什么高薪。即使是local的人拿到这个数的也不再少数。国内靠跳槽涨工资不难,按我现在的背景,在公司里再干两年跳一次,那个五六十万还是有信心的。另外,国内的工资水平涨得很快,和外派的差距现在是越来越少了。其实回国还是留在国外还是看个人。我的意思并不是说回国就一定比国外怎么样。国外确实有比国内好的地方,但也有不如国内的地方。也有人在国外混得不错,我也承认。就我个人而言,国内生活比较适合我。一来经济上我虽然绝对数字比国外低,但我在国外买东西吃饭还要考虑一下,在国内我基本不怎么考虑。有人非要说国外净收入高,我可感觉不到。二来国内文化上适应,朋友也多。国外中国人的娱乐就那么些,交往圈子也窄。国外的生活对我而言比较枯燥,当然有些中国人能完全融入主流社会,不过我孤陋寡闻,还真没见到上完国内大学出来的大陆人真能做的到的。第三呢,我最看重的是事业上的发展,以我的背景,人际网和工作经验,在国内往上走的几率肯定要比国外大。国外的公司不是人际关系不复杂,而是人家根本就没打算让你参与,你没到那个圈子里,只是一个技术工具而已。不少中国人充其量做个team manager而已。我觉得这里有些朋友动不动就拿国内的平均水平比,其实这是一个误区,对自己的定位错了。在美国名牌大学拿学位,几年工作经验,只要人灵活一点,在国内怎么也是top10%里的。至于吃饭报销,手机,打车之类的让各位见笑了,兄弟我还是一穷人。至于我什么回国,真的让各位见笑了。兄弟我真的就是一普通的俗人,回国不是因为什么爱国情结,实实在在是因为在美国混不上去才回国的。一来觉得在中国有机会发展,顺带着发点财。我现在自己搞了几个项目,虽然还没见到钱,但想来也是迟早的事。在美国我从来没这个机会。二来想着生活过的舒服一点,和朋友们在一起吃喝玩乐还有人买单我就是挺高兴的,你要是说我没啥品味,我承认。前面有位老兄说纳税是天经地义的,这说得没错。不过我就挣这么多钱,不管是给中国的贪官污吏还是美国的Uncle Same,我都是想能少交点就少交点,当然我也不会故意去偷税漏税。在美国那么多年,我也没见到谁以多交税为荣的。当然物以类聚,我周围也都是俗人。有人说我给Top 20 school的MBA丢脸了。兄弟我念书就是为了自己的事业发展,没想着给谁挣脸,所以你要不愿意与我为伍,那也随你。Top 20 School的MBA里我算干的中等的,比我好的差的都多了去了,其实做事完全看人,不是念个书拿个学位就能怎么样的。这里这么多人都是精英见多识广,要么是在美国做到VP年薪至少二三十万,要么是思想高尚看不起吃喝玩乐,要是觉得我给中国人丢脸,那我也在这说一句抱歉。我也在中西部住过。生活确实平静但很boring.我认识的朋友里,特别是大城市过来的都很不happy.当然,这只是我个人的感觉和经历。我喜欢热闹,向往挑战的生活,在那种地方我真得很不适应。在美国每年Top 20 BSchool的MBA有一万多,实际上只有很少一部分能去IBank或Management Consulting,大多数MBA最后也就是financial analyst, marketing analyst,product manager之类的工作,更不用说中国学生在语言,文化和networking方面的劣势了。你可能听过不少top MBA的传闻,但不幸的是,那只是传闻而已。但在中国,不仅仅是由于TOP20 MBA在中国很少,美国的MBA学历和经历确实能对你的职业道路帮助很大,再加上文化上的适应和networking,很多人几年之内就升上去了。我个人的经历是在国内的朋友比国外过的好,职业发展好,当然,你所看到的可能不一样。至于报销,手机,Taxi之类的,我说过我不是富人,你也可以认为我在美国是低收入。在美国,我不可能像现在这样每天在饭馆里消费(如果相同的质量的话,差不多$30/meal),我也不可能每天taxi和随便用手机聊天.当然,美国人人都自己开车上班。但在中国,I drive for fun, not for work.我现在工作开展得很好,生活也很开心,当然,这里有不少很有钱的朋友看不起我这样的生活,不过对我来说也没什么。我只是说说个人感觉罢了。关于海归,不妨再说两句。国内的工作没大家想像得那么累。有些人以为在国内拿个几十万就得一天十几个小时不休息,其实没有的事。和在美国一样,不一定拿钱越多就越辛苦,一个月几千块钱的人有时候比一个月几万块钱的还累。只是拿钱越多,责任越大,可供调用的资源越多而已。海归在国内平均收入很高的,和国内平均水平比较基本没有任何意义。中国大部分人口都在农村,没受过高等教育,而海归清一色的至少大学本科以上,更多的还是硕士博士。海归收入高的原因也很简单,中国现在每年进出口贸易几千亿,每年FDI几百亿,更有大量跨国公司直接把工厂销售直接设在中国本地,这么庞大的资本都需要通晓中国文化市场和西方公司管理的人才管理,而中国这类人才的数目和在中国经济中的比重实在是太小了,尤其是高级管理人才和市场人才。这也是为什么很多外国公司的高管是外籍和港台人士的原因,
实实在在是找不到合适的人。这几年海归在公司里升得很快,是因为本身比外籍和港台人相比有优势,一旦经验到了,自然就上去了。说到回国发展,各人有各人的看法。我的个人感觉是原来在国内干得还算可以的,比如年薪十几万以上的,出来后都叫苦,回去的比例也很大。而在国内国企,本地小公司干的都不愿意回去,因为对国内的负面印象深。前面有位加拿大的兄弟说IBM不好进,其实国内的IT外企就是一个相对封闭的圈子,一旦进去了,跳来跳去还是很容易的。  我的$80k年收入那是差不多00年的收入,是MBA前的。如果除去通货膨胀的因素话,相当于现在的9万到十万吧。我所在的地方房价中挡当时在五十万左右,相当于我工资的六倍到七倍。要是在上海,按同样比例,我的国内收入在上海可以买到180万到200万的房子(这还不算住房补贴的因素),从位置到面积都算不错了。至于吃穿住行,在中国的花费我现在比美国小多了。至于所得税,有人说30%不对,可是对于单身的算上州税,联邦税,social security and medicare,就是那么多。美国有美国的好处,中国有中国的好处。我说这些,并不是说每个人选择回国都是对的,只是个人感受。另外,国内的年薪二十万,特别是在外企工作的,比你想象的要舒服得多,可不是你说得像狗一样。你是拿美国的模式套。美国的工资发给你多少就是多少,所有的花费都从你的工资里出,所以总也不够花。不像国内那样有各种各样的补贴报销。一般国内的人说年薪二十万,是不包括奖金和住房补贴,和交通等津贴的。二十万年薪的税不高,算上各种各样的社会保险,也不到20%。就国内的外企而言,级别越高,绝对数目的工资和美国同级别的差别就越少。到VP一级可以说已经没有什么区别了,越到高层购买力的优势在中国越明显。另外随着时代的发展,在中国的business对于外国公司已经是非常重要了,不仅增长快,而且绝对数字和别的国家比起来也不差。举个例子,比如Nokia,中国是全球仅次于美国的第二大市场,或者波音,中国的采购是这几年最大的亮点。现在大量跨国公司的采购都在中国,从服装,玩具,到家用电器甚至一些高科技产品,像Walmart一年的采购有上百亿,这么多钱花在了中国,创造的商机可以想象有多大。从个人发展讲,美国能做到director以上级别的中国人(尤其是那些在大陆念大学以后出来的)占的百分比少之又少,到VP那一级更是屈指可数,在国内机会可就多了,自己创业也容易。我说过回国有个定位问题,有些人总拿中国的平均水平说事,其实根本不make sense.受过高等教育,精通外语,又有专业经验的人,在中国能有多少。可以说,只要你不是在国外混学位,你回来已经在中国前10%里面了。前面有人说上海的人均收入是2万,那可是包括所有人的统计。海归的平均收入绝对要高得多。回来抱怨多的海归有两种,一种是到英国澳洲混学位,本身没什么工作经验的,另外一种是搞纯科学,离市场需求比较远的。我前面说的是北京上海的收入,就现在国内的发展状况,除非你有什么特别的原因,这两个地方是最适合海归发展的。你要非跑到偏远山区发展只能怨你自己。我个人更看好上海及其周边地区,经济发展快,市场也比较规范。国内的绝对收入不能和国外直接比,比如你挣个二十万一年,在上海生活已经可以很舒服了,房子也能买。但两万多年薪的工作在纽约(和美国中小城市比没有意义,完全不同的生活)几乎就活不下去了,房子更是想都不敢想。上海的房子虽然贵,也绝没到纽约LA那么离谱。国内的开销,无非是物质和人工服务,人工绝对是国内便宜,物质上,吃住都是国内便宜,穿上,国内的名牌稍贵一些,但你也不必每天买衣服吧。行上两边差不多。我个人的感觉是考虑到税,物价因素,在中国只要能拿到美国三分之一的税前工资就绝对值得回去。其实回不回去还是对个人的定位,你要把自己定位成刚毕业的学生或者国营企业的工人,那还是留在国外吧,对你来将会来真的不合适。再说说据我所知道的国内收入状况,相信大家也很关心。我先声明我不是什么所谓的精英,对所谓的远大理想崇高责任不感兴趣。我就想自己过得快活,做自己想做的事,顺便发点财,前面有人指责我给中国人丢脸,兄弟我不明白哪里招惹他们了,也不在乎。转入正题。国内的收入可以说是千差万别,我接触的多的是外企。从大的方面来说,外企里美企收入最高,其次是欧洲,在其次是日企,然后是咱们的港澳台胞开的公司。就行业而言,收入最高的当然是投行,管理咨询(就那么几家,大家都知道,我就不多废话了),其次是IT通讯,然后是机械医药快速消费品等传统行业。就拿我所熟悉的IT通讯行业来说(现在IT业的收入与其他行业越拉越近,其他行业的也可以参考),一般有个4,5年以上的技术人员年收入在十万到二十万之间,也有很出色的经验强的能到四五十万,相对而言,做售前的比售后的挣的多,面对客户的比纯研发的挣的多,做销售市场的比做技术的收入高。国内的外企里一般把管理人员分成一线,二线,三线等。一线的就是最低级的manager,一般在二十万以上,最多能到四十万的,二线就是所谓的总监,一般三十万到七八十万,好的能到一百万以上,到了三线就差不多是VP一级,看公司,从一百万到三四百万都有可能。就销售而言,工资定在三十万到七八十万不等,但只有完成销售额才能拿全工资,如果完不成也就拿个百分之六七十,如果超额的话有commission,有时能到工资的几倍,所以做销售很刺激,压力很大。国内的外企里现在有很多人有国外身份,加拿大澳洲的居多,美国的也不少,有没有国外身份收入差别基本没有,都是按职位给钱,只不过医疗社会保险走国籍所在地的要求。现在外企里做高层的(VP或以上)大部分还是港台,美国人,所以给人带来一种有外国身份就能拿高薪的错觉。现在的趋势是香港人做高层的越来越少,海外留学回来的有后来居上的趋势。留学回来的,如果国内国外都有经验是最占优势的,回来起码有个一线manager做,其次是有国外学位经验的,在国内作几年很快就能上来。千万不要什么经验都没有就回来,那可能还不如国内毕业的大学生呢。国内现在对海龟是怎么回事清楚着呢,要靠出钱在外面混两年拿个学位还不如踏踏实实在国内一直干呢。而我说的“技术工具”可能让很多人觉得不痛快。我个人认为中国人在美国是一个教育水平很高的群体,但由于文化语言社会背景的关系,真正能做到高级管理职位的少之又少。美国science曾经登出一篇县局报告说,亚裔占美国总就业人数的4.1%,却占美国生命科学家总数的14.7%,但近200位实验室或分支机构的主任,亚裔只占4.7%。在中国人占尽优势的科学领域尚且如此,更不用提工商界这种对文化社会关系依赖度更强的地方。回去做高级管理职位的海龟的百分比肯定比留在美国的高。我是大学毕业后才到美国的,对于我而言融入主流社会的机会更少,不觉得自己能是那极少数精英中的一员,所以就选条容易的路走。个人情况不一样,对自己的能力判断也不同,我说的比较偏激一点. 本来,各人有各人的兴趣和专长,编编程序没什么不好的。而且,在美国编程序可以说是一种相对收入较高的职业,我的同学朋友不少就是干这个的,过得也很好。就职业发展而言,纯技术有它的局限性。我是学business的,统计结果表明,绝大多数高级管理职位的人都是从三个部门上来的:marketing, finance and accounting。这是事实,不承认不行。说到纳税,我早就说过不会去干偷税漏税的勾当。至于什么天经地义的我不管,只要能在合法的范围里能少纳税,我就感到高兴。“至于上级面前是孙子,下级面前是老子“,我是听了不顺耳。这种style实际上是一种过时的思维。我在公司里无论是对上还是对下都是对事不对人。而且说实在的,每个人的事业发展都有走运背运的时候,你在走运的时候摆架子,背运的时候也别指望别人帮你。至于项目运作,中国这个市场没啥真正的research,重要的在于理解把握客户的需求。技术么,该付多少钱买就付多少。Business is business. 平平淡淡生活,兄弟我就是不喜欢,就活这一辈子,当然是能往上闯就往上闯,省得以后遗憾。

Monday, October 13, 2008

也说念MBA或这个那个转行的

发信人: sffamily1 (sffamily), 信区: SanFrancisco
标 题: 也说念MBA或这个那个转行的
发信站: BBS 未名空间站 (Thu Sep 25 01:03:58 2008)

看了好几个类似的坑,发现一条。
这边的老中想要靠创业来改变自己的比例不高,或者顶多把它作为第二选择。

其实读MBA还是为了找一个更好听的打工职位。不外乎从一个打工的工种变成另外一个。就像多年前有一线工人读夜大,就为了从车间到办公室的转变。而他们的有的不安分的工友,也许那时候就开始辞职或者停薪留职,下海经商了。几年下来你也许做到总监了,高管了,想跳槽,一看最后招你的还是以前的工友,他们也许已经是老板级的,需要你这种经理级的人才帮他们赚钱。我觉得老中要想成气候,一定要每个人都把创业作为第一选择,第一尝试,让市场决定
你是否可以生存,如果不幸被淘汰下来,再去考虑给别人打工。这样其实也会更加安心
你打工的工作。你不试怎么知道你不行?试了才有可能证明你行。这边多数老中光没命的读书拿学位已经浪费无数时光了,如果还是没有彻底改变自己生产地位的观念,就只有活到老,打工到老的前途了。有人说的对,工资不算财富。工资是给工人阶级的。财产才是硬道理。犹太人,看看那些首富,没有人哪怕想过要去念个MBA来作为未来发展的基石。都是选择创业。甚至几乎头几大富翁都是退学生---有本书说得对,各种学位学历,就是资本主义社会给资本家培养合格雇员的一个容易筛选的标准。各种白领职位,无非给你好点的工资和办公环境,好让你开开心心的给老板挣钱有点像养猪场养猪给他们吃好的饲料就是给人类长肉的,奶牛场条件待遇好,就是为了给人类挤更多的奶的。

在弯曲这些年聊过很多人,发现台湾人,香港人,甚至新加坡,马来西亚华人,ABC的创业意识都要强过大陆来的。他们中只有特别安分或者比较能力差些的才会一直安于受雇于人。什么台大毕业生之类都是时刻想创业机会的,吃个饭都要聊聊最近有什么商机。印度人差一些,可能顺民教育深入骨髓,但是也比海外大陆人强,尤其这些年。其实大陆在弯曲的不少,20多年间才有几家大陆人的公司呢?哪怕是失败的?反观前些年的台湾人公司,这些年印度人公司,更不用说老美和犹太人的公司了。每年弯曲有上千家新公司,几个是大陆人开的呢?还是观念问题。这种财富和创业的观念要有家庭的耳濡目染,要有身边的家人或者朋友成功例子的激励,刺激。但是因为大陆60年来资本主义有个大断档,3代人都没有这个概念,只是改革开放后一些非传统方式的暴发户。这些都很难作为模仿的榜样的。不过更年轻一些的国内的新一代,这种观念逐渐有了。但是弯曲的老中还不多见(有,但是不多)。以前欧也是觉得高考,然后留学,拿博士,然后找工作挣工资,天经地义,后来遇到很多人转这个转那个,读MBA什么的,觉得心动,原来还可以这么做,于是也不念博士了,也转了,也去打算MFE或者MBA,可是几年间看着国内的朋友,同学,家人一个个怎么财富增长都这么快?人家也没念多少书,拿过多少学位。于是苦恼了好一阵。觉得路在何方?后来也是偶然的机会前一阵读到外公外婆还有祖父的临去世前整理的档案材料,很震惊的发现,自己的祖先20-30年代都已经是铁矿铁路和连锁百货公司,还有当铺的大股东了。有20岁没到就和同乡开煤矿的。有引进德国机器开面粉厂的。不过这些东西因为祖父辈都参加革命脱离旧家庭,我父母和我自己都从未听说过。这种震撼是颠覆性的。更多的是一种羞愧的成分在里面,觉得真是一代不如一代的感觉,不指自己的学识,而是自己的见识。即使和偶cousin们比,论学位,学历都比他们高一些,可是这过去十年我在使劲读书,然后使劲打工当硅谷小农,他们是一直在创业,从白手起家,到艰难发展,现在回头看,人家已经大成功了,已经是大资本家了,咱只是混日子的高级技工而已。所以最近一直在重新思考自己原来给自己设计的路是不是需要调整了。

现在倒是越来越有要自己做点什么的野心。想从小的,简单的开始练练手。看看能不能找回失去的创业的DNA. -- 这要向afei同鞋学习!

我觉得大陆来的老中在湾区的应该多学学别的族裔,甚至学学我们的台湾同胞,多些创业的气氛。大陆的校友聚会,或者团体聚会,很多就是为了娱乐一下,或者单身俱乐部,要不就是网络一下好从一个打工职位换到另一个。而很多湾区很好的职业行业协会,不少都是台湾人牵头的,讨论的主题总是离不了融资,创业,创造就业机会。其实创业也不一定非高科技不可。先业余弄点什么练一练,我觉得都比MBA更有意义。如果周围的人都有创业的风气了,我觉得老中在湾区才有希望。才对得起自己的这么多年艰苦奋斗,为别人做牛做马的毅力和努力。(另:我一直收看中央4的财富故事会,讲各种人在大陆这几年创业的故事,因为政府都在鼓励年轻人创业,总是挺受鼓舞的)

Thursday, September 25, 2008

Disadvantage of C++ Templates

What is the disadvantage of a template function?

A template function cannot be distributed in the obj form. This is because, the parameters with which the template function is going to be called is decided at the run time only. Therefore an obj form of a template function cannot be made by merely compiling it.

But templates have a few negative aspects that are not widely explored. First, since C++ does not have binary run-time extensibility, templates can't be linked and distributed as a library. They must be compiled at compile time, and, therefore, all implementations of a template algorithm must be included in the header files in their entirety. You can easily see this by analyzing the STL standard header files.

----
Both macros and templates are expanded at compile time. Macros are always expanded inline; templates can also be expanded as inline functions when the compiler deems it appropriate. Thus both function-like macros and function templates have no run-time overhead.
However, templates are generally considered an improvement over macros for these purposes. Templates are type-safe. Templates avoid some of the common errors found in code that makes heavy use of function-like macros. Perhaps most importantly, templates were designed to be applicable to much larger problems than macros. The definition of a function-like macro must fit on a single logical line of code.
There are three primary drawbacks to the use of templates. First, many compilers historically have very poor support for templates, so the use of templates can make code somewhat less portable. Second, almost all compilers produce confusing, unhelpful error messages when errors are detected in template code. This can make templates difficult to develop. Third, each use of a template may cause the compiler to generate extra code (an instantiation of the template), so the indiscriminate use of templates can lead to code bloat, resulting in excessively large executables.
The other big disadvantage of templates is that to replace a #define like max which acts identically with dissimilar types or function calls is impossible. Templates have replaced using #defines for complex functions but not for simple stuff like max(a,b). For a full discussion on trying to create a template for the #define max, see the paper "Min, Max and More" that Scott Meyer wrote for C++ Report in January 1995.
The biggest advantage of using templates, is that a complex algorithm can have a simple interface that the compiler then uses to choose the correct implementation based on the type of the arguments. For instance, a searching algorithm can take advantage of the properties of the container being searched. This technique is used throughout the C++ standard library.

----

The biggest advantage of using templates, is that a complex algorithm can have a simple interface that the compiler then uses to choose the correct implementation based on the type of the arguments.

inline virtual function?

http://msdn.microsoft.com/en-us/magazine/cc301407.aspx

Inline Virtual Functions, AVI Files in EXEs, and the DynPrompt Sample App
Paul DiLascia
Code for this article: CQA0600.exe (47KB)
Q How does C++ handle inline virtual functions? When a function is inline and virtual, will code substitution take place or is the call resolved using the vtable?
G.N. Rajagopal
A The answer is, it depends. To see why, let's consider each caseâ€"inline and virtualâ€"separately. Normally, an inline function is expanded, well, inline.
class CFoo {
private:
int val;
public:
int GetVal() { return val; }
int SetVal(int v) { return val=v; }
};
In this situation, if you write
CFoo x;
x.SetVal(17);
int y = x.GetVal();
then the compiler generates the code as if you'd written:
CFoo x;
x.val = 17;
int y = x.val;
Of course you can't do this because val is private. Inline functions give you the advantage of data hiding without paying the price of a function call. So much for inline functions. Virtual functions give you polymorphism, which means derived classes can implement the same function differently. Suppose GetVal is now declared virtual and you have a second class, CFoo2, with a different implementation:
class CFoo2 : public CFoo {
public:
// virtual in base class too!
virtual int CFoo2::GetVal() {
return someOtherVal;
}
};
If pFoo is a pointer to a CFoo or CFoo2, then pFoo->GetVal will call the member function for whichever class pFoo really points toâ€"CFoo or CFoo2. This is C++ 101, and you should know it like the back of your hand. But what happens if a function is both virtual and inline? Remember, there are two ways to make a function inline: by using the inline keyword in the function definition, as in
inline CFoo::GetVal() { return val; }
or by coding the function body inline within the class declaration, as in the previous CFoo2::GetVal example. So if you include the body of your virtual function within the class declaration
class CFoo {
public:
virtual int GetVal() { return val; }
};
then you are telling the compiler you want GetVal to be both inline and virtual. This doesn't seem to make sense, for how can polymorphism work if the function is expanded inline? The answer, of course, is that it can't. Or can it? The first rule the compiler follows when it encounters such a beast is this: whatever happens, polymorphism must work. If you have a pointer to a CFoo object, then pFoo->GetVal is guaranteed to call the right function. In general, this means the GetVal functions will be instantiated as real (noninline) functions, with vtable entries pointing to them. But that doesn't mean the function can't ever be expanded! Consider this code again:
CFoo x;
x.SetVal(17);
int y = x.GetVal();
The compiler knows that x is really a CFoo, not a CFoo2, since the stack object is explicitly declared. There's no way x could really be a CFoo2. So it's safe to expand SetVal/GetVal inline. If you write this more complex code
CFoo x;
CFoo* pfoo=&x;
pfoo->SetVal(17);
int y = pfoo->GetVal();
���
CFoo2 x2;
pfoo = &x2;
pfoo->SetVal(17); //etc.
the compiler knows that pfoo points to x the first time and x2 the second time, so again it's safe to expand the virtual functions. You can dream up ever more complex examples, where the type of object pfoo points to is always known, but most compilers won't do any heavy analysis. Even in the preceding example, some compilers will do the safe thing, which is to instantiate the function and call through a vtable. Indeed, the compiler is free to ignore the inline requirement and always use the vtable. The only absolute rule is that the code must work; that is, virtual functions must behave polymorphically. In general, inlineâ€"whether explicit or implicitâ€"is a hint, not a mandate, just like register. (Does anyone remember register? It asks the compiler to use a machine register for a variable if it can.) The compiler can refuse to expand even a nonvirtual inline function if it wants to, and the first C++ compilers often complained, "inline abortedâ€"function too big." Certainly if an inline function calls itself, or if you pass its address somewhere, the compiler must generate a normal (outline?) function. And, of course, inline functions are not expanded in debug builds, or if you set a compiler option preventing it. The only way to really know what your compiler is doing is to look at the code it generates. For the Microsoft® compiler, you can compile with -FA to generate an assembly listing. You don't need to be an assembler jock to know what's going on. I encourage you to perform this experiment; it's good for the soul to see what the machine is actually doing, and you can learn a lot poking around assembly listings. For now, I'll spare you that agony. The topic of inline functions is more complex than you might think at first. There are many circumstances that force the compiler to generate a normal function: recursion, taking the address of your function, functions that are too big, and virtual functions.

Here's another consideration: if the compiler decides to instantiate your inline function, where does it put the function? Which module does it go into? Usually, classes are declared in header (.h) files. So if mumble.cpp includes foo.h and the compiler decides it has to instantiate CFoo:: GetVal, it will instantiate it as a static function in mumble.cpp. If 10 modules include foo.h, the compiler could generate up to 10 copies of your virtual function. In fact, you could end up with objects of the same type with vtables pointing to different copies of GetVal. Yuk! Some linkers are smart enough to eliminate the redundancies at link time, but in general you can't be sure. So the bottom line is: it's best not to use inline virtual functions, since they're almost never expanded anyway. Even if your function is just one line, you're better off putting it in the module (.cpp file) along with the other class functions. Of course, programmers often put short virtual functions in the class declarationâ€"not because they expect the function to be expanded inline, but because it's more convenient and readable.

http://www.parashift.com/c++-faq-lite/value-vs-ref-semantics.html#faq-31.6

[31.6] Are "inline virtual" member functions ever actually "inlined"?
Occasionally...
When the object is referenced via a pointer or a reference, a call to a virtual function cannot be inlined, since the call must be resolved dynamically. Reason: the compiler can't know which actual code to call until run-time (i.e., dynamically), since the code may be from a derived class that was created after the caller was compiled.
Therefore the only time an inline virtual call can be inlined is when the compiler knows the "exact class" of the object which is the target of the virtual function call. This can happen only when the compiler has an actual object rather than a pointer or reference to an object. I.e., either with a local object, a global/static object, or a fully contained object inside a composite.
Note that the difference between inlining and non-inlining is normally much more significant than the difference between a regular function call and a virtual function call. For example, the difference between a regular function call and a virtual function call is often just two extra memory references, but the difference between an inline function and a non-inline function can be as much as an order of magnitude (for zillions of calls to insignificant member functions, loss of inlining virtual functions can result in 25X speed degradation! [Doug Lea, "Customization in C++," proc Usenix C++ 1990]).
A practical consequence of this insight: don't get bogged down in the endless debates (or sales tactics!) of compiler/language vendors who compare the cost of a virtual function call on their language/compiler with the same on another language/compiler. Such comparisons are largely meaningless when compared with the ability of the language/compiler to "inline expand" member function calls. I.e., many language implementation vendors make a big stink about how good their dispatch strategy is, but if these implementations don't inline member function calls, the overall system performance would be poor, since it is inlining —not dispatching— that has the greatest performance impact.

Tuesday, September 23, 2008

virtual constructor

An idiom that allows you to do something that C++ doesn't directly support.

You can get the effect of a virtual constructor by a virtual clone() member function (for copy constructing), or a virtual create() member function (for the default constructor).

class Shape {
public:
virtual ~Shape() { }
// A virtual destructor
virtual void draw() = 0;
// A pure virtual function
virtual void move() = 0;
...
virtual Shape* clone() const = 0;
// Uses the copy constructor
virtual Shape* create() const = 0;
// Uses the default constructor
};

class Circle : public Shape {
public:
Circle* clone() const;
// Covariant Return Types; see below
Circle* create() const;
// Covariant Return Types; see below
...
};

Circle* Circle::clone() const { return new Circle(*this); }
Circle* Circle::create() const { return new Circle(); }

In the clone() member function, the new Circle(*this) code calls Circle's copy constructor to copy the state of this into the newly created Circle object. (Note: unless Circle is known to be final (AKA a leaf), you can reduce the chance of slicing by making its copy constructor protected.) In the create() member function, the new Circle() code calls Circle's default constructor.

Users use these as if they were "virtual constructors":

void userCode(Shape& s)
{
Shape* s2 = s.clone();
Shape* s3 = s.create();
...
delete s2;
// You need a virtual destructor here
delete s3;
}

This function will work correctly regardless of whether the Shape is a Circle, Square, or some other kind-of Shape that doesn't even exist yet.

Note: The return type of Circle's clone() member function is intentionally different from the return type of Shape's clone() member function. This is called Covariant Return Types, a feature that was not originally part of the language. If your compiler complains at the declaration of Circle* clone() const within class Circle (e.g., saying "The return type is different" or "The member function's type differs from the base class virtual function by return type alone"), you have an old compiler and you'll have to change the return type to Shape*.

Note: If you are using Microsoft Visual C++ 6.0, you need to change the return types in the derived classes to Shape*. This is because MS VC++ 6.0 does not support this feature of the language. Please do not write me about this; the above code is correct with respect to the C++ Standard (see 10.3p5); the problem is with MS VC++ 6.0. Fortunately covariant return types are properly supported by MS VC++ 7.0.

Reference:

http://www.parashift.com/c++-faq-lite/virtual-functions.html#faq-20.8


Monday, September 22, 2008

Factory Pattern (a.k.a. virtual constructor)

Factory Method helps to model an interface for creating an object which at creation time can let its subclasses decide which class to instantiate. We call this a Factory Pattern since it is responsible for "Manufacturing" an Object. It helps instantiate the appropriate Subclass by creating the right Object from a group of related classes. The Factory Pattern promotes loose coupling by eliminating the need to bind application-specific classes into the code.

The Factory Pattern is all about "Define an interface for creating an object, but let the subclasses decide which class to instantiate. The Factory method lets a class defer instantiation to subclasses" Thus, as defined by Gamma et al, "The Factory Method lets a class defer instantiation to subclasses".

This pattern is used when a class (the Creator) does not know beforehand all the subclasses that it will create.

* Factory methods are common in toolkits and frameworks where library code needs to create objects of types which may be subclassed by applications using the framework.
* Parallel class hierarchies often require objects from one hierarchy to be able to create appropriate objects from another.

Example: (http://en.wikibooks.org/wiki/More_C%2B%2B_Idioms/Virtual_Constructor)
class Employee
{
public:
virtual ~Employee () {} // Native support for polymorphic destruction.
virtual Employee * create () const = 0; // Virtual constructor (creation)
virtual Employee * clone () const = 0; // Virtual constructor (copying)
};
class Manager : public Employee // "is-a" relationship
{
public:
Manager (); // Default constructor
Manager (Manager const &); // Copy constructor
~Manager () {} // Destructor
Manager * create () const // Virtual constructor (creation)
{
return new Manager();
}
Manager * clone () const // Virtual constructor (copying)
{
return new Manager (*this);
}
};
class Programmer : public Employee { /* Very similar to the Manager class */ };
Employee * duplicate (Employee const & e)
{
return e.clone(); // Using virtual constructor idiom.
}

More effective c++ Item 25

Because the function creates new objects, it acts much like a constructor, but because it can create different types of objects, we call it a virtual constructor. A virtual constructor is a function that creates different types of objects depending on the input it is given. Virtual constructors are useful in many contexts, only one of which is reading object information from disk (or off a network connection or from a tape).

A particular kind of virtual constructor — the virtual copy constructor — is also widely useful. A virtual copy constructor returns a pointer to a new copy of the object invoking the function.

etc.).


References:

http://gsraj.tripod.com/design/creational/factory/factory.html
http://en.wikipedia.org/wiki/Factory_method_pattern

Sunday, September 21, 2008

C++ Concepts

Abstract classes v.s Interfaces
1. Abstract classes CANNOT be instantiated and only instances of concrete subclasses can be created.
2. An interface has no data members and no method definitions (only pure virtual functions)


C++ v.s Java v.s C#
1. C++ has no garbage collection and supports multiple inheritance
2. Default C++ & C# methods are nonvirtual, Nonstatic Java methods are virtual

Saturday, September 20, 2008

Thursday, September 18, 2008

Abbreviations

PTO: Paid Time Off

OOTO: Out Of The Office

Wednesday, September 17, 2008

Binary Search Tree

1. Design an algorithm and write code to find the common ancestor of two nodes in a tree

Linked list

1. Check if there is a common node in 2 linked lists.

Solution: All we need to do is to first calculate len=len1-len2 (len1>len2, as discussed above). Point p1 and p2 to list1 (the longer one) and list2 respectively. Then step only p1 for "len" no. of nodes. After this we are guaranteed that p1 and p2 are equidistant from the common node. So now start stepping p1 and p2 simultaneously until p1==p2. This will the common node. This is a simple O(n) solution.

Wednesday, July 30, 2008

Monday, July 28, 2008

You've got to find what you love_Steve Jobs

Stanford Report, June 14, 2005
'You've got to find what you love,' Jobs says

Printable Version
This is the text of the Commencement address by Steve Jobs, CEO of Apple Computer and of Pixar Animation Studios, delivered on June 12, 2005.

I am honored to be with you today at your commencement from one of the finest universities in the world. I never graduated from college. Truth be told, this is the closest I've ever gotten to a college graduation. Today I want to tell you three stories from my life. That's it. No big deal. Just three stories.

The first story is about connecting the dots.

I dropped out of Reed College after the first 6 months, but then stayed around as a drop-in for another 18 months or so before I really quit. So why did I drop out?

It started before I was born. My biological mother was a young, unwed college graduate student, and she decided to put me up for adoption. She felt very strongly that I should be adopted by college graduates, so everything was all set for me to be adopted at birth by a lawyer and his wife. Except that when I popped out they decided at the last minute that they really wanted a girl. So my parents, who were on a waiting list, got a call in the middle of the night asking: "We have an unexpected baby boy; do you want him?" They said: "Of course." My biological mother later found out that my mother had never graduated from college and that my father had never graduated from high school. She refused to sign the final adoption papers. She only relented a few months later when my parents promised that I would someday go to college.

And 17 years later I did go to college. But I naively chose a college that was almost as expensive as Stanford, and all of my working-class parents' savings were being spent on my college tuition. After six months, I couldn't see the value in it. I had no idea what I wanted to do with my life and no idea how college was going to help me figure it out. And here I was spending all of the money my parents had saved their entire life. So I decided to drop out and trust that it would all work out OK. It was pretty scary at the time, but looking back it was one of the best decisions I ever made. The minute I dropped out I could stop taking the required classes that didn't interest me, and begin dropping in on the ones that looked interesting.

It wasn't all romantic. I didn't have a dorm room, so I slept on the floor in friends' rooms, I returned coke bottles for the 5¢ deposits to buy food with, and I would walk the 7 miles across town every Sunday night to get one good meal a week at the Hare Krishna temple. I loved it. And much of what I stumbled into by following my curiosity and intuition turned out to be priceless later on. Let me give you one example:

Reed College at that time offered perhaps the best calligraphy instruction in the country. Throughout the campus every poster, every label on every drawer, was beautifully hand calligraphed. Because I had dropped out and didn't have to take the normal classes, I decided to take a calligraphy class to learn how to do this. I learned about serif and san serif typefaces, about varying the amount of space between different letter combinations, about what makes great typography great. It was beautiful, historical, artistically subtle in a way that science can't capture, and I found it fascinating.

None of this had even a hope of any practical application in my life. But ten years later, when we were designing the first Macintosh computer, it all came back to me. And we designed it all into the Mac. It was the first computer with beautiful typography. If I had never dropped in on that single course in college, the Mac would have never had multiple typefaces or proportionally spaced fonts. And since Windows just copied the Mac, its likely that no personal computer would have them. If I had never dropped out, I would have never dropped in on this calligraphy class, and personal computers might not have the wonderful typography that they do. Of course it was impossible to connect the dots looking forward when I was in college. But it was very, very clear looking backwards ten years later.

Again, you can't connect the dots looking forward; you can only connect them looking backwards. So you have to trust that the dots will somehow connect in your future. You have to trust in something — your gut, destiny, life, karma, whatever. This approach has never let me down, and it has made all the difference in my life.

My second story is about love and loss.

I was lucky — I found what I loved to do early in life. Woz and I started Apple in my parents garage when I was 20. We worked hard, and in 10 years Apple had grown from just the two of us in a garage into a $2 billion company with over 4000 employees. We had just released our finest creation — the Macintosh — a year earlier, and I had just turned 30. And then I got fired. How can you get fired from a company you started? Well, as Apple grew we hired someone who I thought was very talented to run the company with me, and for the first year or so things went well. But then our visions of the future began to diverge and eventually we had a falling out. When we did, our Board of Directors sided with him. So at 30 I was out. And very publicly out. What had been the focus of my entire adult life was gone, and it was devastating.

I really didn't know what to do for a few months. I felt that I had let the previous generation of entrepreneurs down - that I had dropped the baton as it was being passed to me. I met with David Packard and Bob Noyce and tried to apologize for screwing up so badly. I was a very public failure, and I even thought about running away from the valley. But something slowly began to dawn on me — I still loved what I did. The turn of events at Apple had not changed that one bit. I had been rejected, but I was still in love. And so I decided to start over.

I didn't see it then, but it turned out that getting fired from Apple was the best thing that could have ever happened to me. The heaviness of being successful was replaced by the lightness of being a beginner again, less sure about everything. It freed me to enter one of the most creative periods of my life.

During the next five years, I started a company named NeXT, another company named Pixar, and fell in love with an amazing woman who would become my wife. Pixar went on to create the worlds first computer animated feature film, Toy Story, and is now the most successful animation studio in the world. In a remarkable turn of events, Apple bought NeXT, I returned to Apple, and the technology we developed at NeXT is at the heart of Apple's current renaissance. And Laurene and I have a wonderful family together.

I'm pretty sure none of this would have happened if I hadn't been fired from Apple. It was awful tasting medicine, but I guess the patient needed it. Sometimes life hits you in the head with a brick. Don't lose faith. I'm convinced that the only thing that kept me going was that I loved what I did. You've got to find what you love. And that is as true for your work as it is for your lovers. Your work is going to fill a large part of your life, and the only way to be truly satisfied is to do what you believe is great work. And the only way to do great work is to love what you do. If you haven't found it yet, keep looking. Don't settle. As with all matters of the heart, you'll know when you find it. And, like any great relationship, it just gets better and better as the years roll on. So keep looking until you find it. Don't settle.

My third story is about death.

When I was 17, I read a quote that went something like: "If you live each day as if it was your last, someday you'll most certainly be right." It made an impression on me, and since then, for the past 33 years, I have looked in the mirror every morning and asked myself: "If today were the last day of my life, would I want to do what I am about to do today?" And whenever the answer has been "No" for too many days in a row, I know I need to change something.

Remembering that I'll be dead soon is the most important tool I've ever encountered to help me make the big choices in life. Because almost everything — all external expectations, all pride, all fear of embarrassment or failure - these things just fall away in the face of death, leaving only what is truly important. Remembering that you are going to die is the best way I know to avoid the trap of thinking you have something to lose. You are already naked. There is no reason not to follow your heart.

About a year ago I was diagnosed with cancer. I had a scan at 7:30 in the morning, and it clearly showed a tumor on my pancreas. I didn't even know what a pancreas was. The doctors told me this was almost certainly a type of cancer that is incurable, and that I should expect to live no longer than three to six months. My doctor advised me to go home and get my affairs in order, which is doctor's code for prepare to die. It means to try to tell your kids everything you thought you'd have the next 10 years to tell them in just a few months. It means to make sure everything is buttoned up so that it will be as easy as possible for your family. It means to say your goodbyes.

I lived with that diagnosis all day. Later that evening I had a biopsy, where they stuck an endoscope down my throat, through my stomach and into my intestines, put a needle into my pancreas and got a few cells from the tumor. I was sedated, but my wife, who was there, told me that when they viewed the cells under a microscope the doctors started crying because it turned out to be a very rare form of pancreatic cancer that is curable with surgery. I had the surgery and I'm fine now.

This was the closest I've been to facing death, and I hope its the closest I get for a few more decades. Having lived through it, I can now say this to you with a bit more certainty than when death was a useful but purely intellectual concept:

No one wants to die. Even people who want to go to heaven don't want to die to get there. And yet death is the destination we all share. No one has ever escaped it. And that is as it should be, because Death is very likely the single best invention of Life. It is Life's change agent. It clears out the old to make way for the new. Right now the new is you, but someday not too long from now, you will gradually become the old and be cleared away. Sorry to be so dramatic, but it is quite true.

Your time is limited, so don't waste it living someone else's life. Don't be trapped by dogma — which is living with the results of other people's thinking. Don't let the noise of others' opinions drown out your own inner voice. And most important, have the courage to follow your heart and intuition. They somehow already know what you truly want to become. Everything else is secondary.

When I was young, there was an amazing publication called The Whole Earth Catalog, which was one of the bibles of my generation. It was created by a fellow named Stewart Brand not far from here in Menlo Park, and he brought it to life with his poetic touch. This was in the late 1960's, before personal computers and desktop publishing, so it was all made with typewriters, scissors, and polaroid cameras. It was sort of like Google in paperback form, 35 years before Google came along: it was idealistic, and overflowing with neat tools and great notions.

Stewart and his team put out several issues of The Whole Earth Catalog, and then when it had run its course, they put out a final issue. It was the mid-1970s, and I was your age. On the back cover of their final issue was a photograph of an early morning country road, the kind you might find yourself hitchhiking on if you were so adventurous. Beneath it were the words: "Stay Hungry. Stay Foolish." It was their farewell message as they signed off. Stay Hungry. Stay Foolish. And I have always wished that for myself. And now, as you graduate to begin anew, I wish that for you.Publish Post

Stay Hungry. Stay Foolish.

Thank you all very much.

今天,有荣幸来到各位从世界上最好的学校之一毕业的毕业典礼上。
我从来没从大学毕业。说实话,这是我离大学毕业最近的一刻。
今天,我只说三个故事,不谈大道理,三个故事就好。

第一个故事,是关于人生中的点点滴滴怎么串连在一起。

我在里德学院(Reedcollege)待了六个月就办休学了。到我退学前,一共休学了十八个月。那么,我为什么休学?

这 得从我出生前讲起。我的亲生母亲当时是个研究生,年轻未婚妈妈,她决定让别人收养我。她强烈觉得应该让有大学毕业的人收养我,所以我出生时,她就准备让我 被一对律师夫妇收养。但是这对夫妻到了最后一刻反悔了,他们想收养女孩。所以在等待收养名单上的一对夫妻,我的养父母,在一天半夜里接到一通电话,问他们 「有一名意外出生的男孩,你们要认养他吗?」而他们的回答是「当然要」。后来,我的生母发现,我现在的妈妈从来没有大学毕业,我现在的爸爸则连高中毕业也 没有。她拒绝在认养文件上做最后签字。直到几个月后,我的养父母同意将来一定会让我上大学,她才软化态度。

十七年后,我上大学了。但是当时我无知选了一所学费几乎跟史丹佛一样贵的大学,我那工人阶级的父母所有积蓄都花在我的学费上。六个月后,我看不出念这个书的价值何在。那时候,我不知道这辈子要乾什么,也不知道念大学能对我有什么帮助,而且我为了念这个书,
花 光了我父母这辈子的所有积蓄,所以我决定休学,相信船到桥头自然直。当时这个决定看来相当可怕,可是现在看来,那是我这辈子做过最好的决定之一。当我休学 之后,我再也不用上我没兴趣的必修课,把时间拿去听那些我有兴趣的课。这一点也不浪漫。我没有宿舍,所以我睡在友人家里的地板上,靠着回收可乐空罐的五先 令退费买吃的,每个星期天晚上得走七哩的路绕过大半个镇去印度教的Hare Krishna 神庙吃顿好料。我喜欢HareKrishna神庙的好料。追寻我的好奇与直觉,我所驻足的大部分事物,后来看来都成了无价之宝。

举例来说:

当 时里德学院有着大概是全国最好的书法指导。在整个校园内的每一张海报上,每个抽屉的标签上,都是美丽的手写字。因为我休学了,可以不照正常选课程序来,所 以我跑去学书法。我学了serif 与san serif 字体,学到在不同字母组合间变更字间距,学到活版印刷伟大的地方。书法的美好、历史感与艺术感是科学所无法捕捉的,我觉得那很迷人。我没预期过学的这些东 西能在我生活中起些什么实际作用,不过十年后,当我在设计第一台麦金塔时,我想起了当时所学的东西,所以把这些东西都设计进了麦金塔里,这是第一台能印刷 出漂亮东西的计算机。如果我没沉溺于那样一门课里,麦金塔可能就不会有多重字体跟变间距字体了。又因为Windows抄袭了麦金塔的使 用方式,如果当年我没这样做,大概世界上所有的个人计算机都不会有这些东西,印不出现在我们看到的漂亮的字来了。当然,当我还在大学里时,不可能把这些点 点滴滴预先串在一起,但是这在十年后回顾,就显得非常清楚。我再说一次,你不能预先把点点滴滴串在一起;唯有未来回顾时,你才会明白那些点点滴滴是如何串 在一起的。

所以你得相信,你现在所体会的东西,将来多少会连接在一块。你得信任某个东西,直觉也好,命运也好,生命也好,或者业力。这种作法从来没让我失望,也让我的人生整个不同起来。

我的第二个故事,有关爱与失去。

我 好运-年轻时就发现自己爱做什么事。我二十岁时,跟Steve Wozniak在我爸妈的车库里开始了苹果计算机的事业。我们拼命工作,苹果计算机在十年间从一间车库里的两个小伙子扩展成了一家员工超过四千人、市价二 十亿美金的公司,在那之前一年推出了我们最棒的作品-麦金塔,而我才刚迈入人生的第三十个年头,然后被炒鱿鱼。

要怎么让自己创办的公司炒自己鱿鱼?

好 吧,当苹果计算机成长后,我请了一个我以为他在经营公司上很有才乾的家伙来,他在头几年也确实乾得不错。可是我们对未来的愿景不同,最后只好分道扬镳,董 事会站在他那边,炒了我鱿鱼,公开把我请了出去。曾经是我整个成年生活重心的东西不见了,令我不知所措。有几个月,我实在不知道要乾什么好。我觉得我令企 业界的前辈们失望-我把他们交给我的接力棒弄丢了。我见了创办HP的David Packard跟创办Intel的Bob Noyce,跟他们说我很抱歉把事情搞砸得很厉害了。我成了公众的非常负面示范,我甚至想要离开硅谷。但是渐渐的,我发现,我还是喜爱着我做过的事情,在 苹果的日子经历的事件没有丝毫改变我爱做的事。我被否定了,可是我还是爱做那些事情,所以我决定从头来过。

当时我没发现,但是现在看来, 被苹果计算机开除,是我所经历过最好的事情。成功的沉重被从头来过的轻松所取代,每件事情都不那么确定,让我自由进入这辈子最有创意的年代。接下来五年, 我开了一家叫做 NeXT的公司,又开一家叫做Pixar的公司,也跟后来的老婆谈起了恋爱。Pixar接着制作了世界上第一部全计算机动画电影,玩具总动员,现在是世界 上 最成功的动画制作公司。然后,苹果计算机买下了NeXT,我回到了苹果,我们在NeXT发展的技术成了苹果计算机后来复兴的核心。我也有了个美妙的家庭。

我 很确定,如果当年苹果计算机没开除我,就不会发生这些事情。这帖药很苦口,可是我想苹果计算机这个病人需要这帖药。有时候,人生会用砖头打你的头。不要丧 失信心。我确信,我爱我所做的事情,这就是这些年来让我继续走下去的唯一理由。你得找出你爱的,工作上是如此,对情人也是如此。

你的工作将填满你的一大块人生,唯一获得真正满足的方法就是做你相信是伟大的工作,而唯一做伟大工作的方法是爱你所做的事。如果你还没找到这些事,继续找,别停顿。尽你全心全力,你知道你一定会找到。而且,如同任何伟大的关系,事情只会随着时间愈来愈好。
所以,在你找到之前,继续找,别停顿。

我的第三个故事,关于死亡。

当 我十七岁时,我读到一则格言,好像是「把每一天都当成生命中的最后一天,你就会轻松自在。」这对我影响深远,在过去33年里,我每天早上都会照镜子,自 问:「如果今天是此生最后一日,我今天要乾些什么?」每当我连续太多天都得到一个「没事做」的答案时,我就知道我必须有所变革了。提醒自己快死了,是我在 人生中下重大决定时,所用过最重要的工具。因为几乎每件事-所有外界期望、所有名誉、所有对困窘或失败的恐惧-在面对死亡时,都消失了,只有最重要的东西 才会留下。提醒自己快死了,是我所知避免掉入自己有东西要失去了的陷阱里最好的方法。

人生不带来,死不带去,没什么道理不顺心而为。

一 年前,我被诊断出癌症。我在早上七点半作断层扫描,在胰脏清楚出现一个肿瘤,我连胰脏是什么都不知道。医生告诉我,那几乎可以确定是一种不治之症,我大概 活不到三到六个月了。医生建议我回家,好好跟亲人们聚一聚,这是医生对临终病人的标准建议。那代表你得试着在几个月内把你将来十年想跟小孩讲的话讲完。那 代表你得把每件事情搞定,家人才会尽量轻松。那代表你得跟人说再见了。我整天想着那个诊断结果,那天晚上做了一次切片,从喉咙伸入一个内视镜,从胃进肠 子,插了根针进胰脏,取了一些肿瘤细胞出来。我打了镇静剂,不醒人事,但是我老婆在场。她后来跟我说,当医生们用显微镜看过那些细胞后,他们都哭了,因为 那是非常少见的一种胰脏癌,可以用手术治好。所以我接受了手术,康复了。

这是我最接近死亡的时候,我希望那会继续是未来几十年内最接近的一次。经历此事后,我可以比之前死亡只是抽象概念时要更肯定告诉你们下面这些:

没 有人想死。即使那些想上天堂的人,也想活着上天堂。但是死亡是我们共有的目的地,没有人逃得过。这是注定的,因为死亡简直就是生命中最棒的发明,是生命变 化的媒介,送走老人们,给新生代留下空间。现在你们是新生代,但是不久的将来,你们也会逐渐变老,被送出人生的舞台。抱歉讲得这么戏剧化,但是这是真的。

你们的时间有限,所以不要浪费时间活在别人的生活里。不要被信条所惑-盲从信条就是活在别人思考结果里。不要让别人的意见淹没了你内在的心声。最重要的,拥有跟随内心与直觉的勇气,你的内心与直觉多少已经知道你真正想要成为什么样的人。任何其它事物都是次要的。

在 我年轻时,有本神奇的杂志叫做 Whole Earth Catalog,当年我们很迷这本杂志。那是一位住在离这不远的Menlo Park的Stewart Brand发行的,他把杂志办得很有诗意。那是1960年代末期,个人计算机跟桌上出版还没发明,所有内容都是打字机、剪刀跟拍立得相机做出来的。
杂 志内容有点像印在纸上的Google,在Google出现之前35年就有了:理想化,充满新奇工具与神奇的注记。Stewart跟他的出版团队出了好几 期Whole Earth Catalog,然后出了停刊号。当时是1970年代中期,我正是你们现在这个年龄的时候。在停刊号的封底,有张早晨乡间小路的照片,那种你去爬山时会经 过的乡间小路。

在照片下有行小字:

求知若饥,虚心若愚。

那是他们亲笔写下的告别讯息,我总是以此自许。
当你们毕业,展开新生活,我也以此期许你们。

求知若饥,虚心若愚。

非常谢谢大家。

Thursday, July 24, 2008

IO Benchmark


UNIX I/O Benchmarks
Bonnie++ - NEW!
Greatly improved disk I/O benchmark based on the code for Bonnie by Tim Bray. Bonnie++, rewritten in C++ by Russell Coker (russell@coker.com.au), adds the facility to test more than 2Gb of storage on 32-bit machines, and tests for file creat(), stat(), unlink() operations.

Bonnie v.2.0.6
One of the best "open systems" benchmarks available. It can be compiled under different UNIX flavors. We have successfully run it under SCO UNIX, Linux, Solaris, and BSDI. It should also compile with minimal changes under other UNIXes.

IOzone - UPDATED
Another great benchmark, in our opinion. The benchmark generates and measures a variety of file operations. IOzone is useful for performing broad filesystem analysis of a vendor's computer platform. It can also be used for NFS performance testing and the latest version now supports cluster testing as well. IOzone had been ported to numerous UNIX OSes and Windows NT. Read more about it and download the source by clicking on the link above.

Xbench - NEW!
Xbench is a a comprehensive benchmarking solution for Mac OS X. In addition to various system component benchmarks, it provides performance testing capabilities for sequential and random uncached disk I/O performance.

IOstone v. C/II
IOstone is a multi-platform disk, file I/O and buffer cache efficiencies benchmark program. This benchmark was originally created for UNIX and later ported to OS/2 and DOS. Included in this archive are the OS/2 and DOS executables with source code.

Disktest
Disktest allows any direct access device (and some sequential devices) to be tested while UNIX is still available to other users. Care should be taken to make the device which is to be tested unavailable to other system users.

IOBENCH
Excellent I/O throughput and fixed workload benchmark for UNIX. There are two versions of IOBENCH contained in sub-directories of this directory. These two versions contain the same source files and differ only in the scripts that drive the benchmark. Directory 073.iobench contains the throughput variant; directory 084.iobenchpf contains the fixed workload variant. This is the SPEC 2.6 distribution of IOBENCH.

IOCALL
IOCALL measures OS performance, in fact that is nearly all it measures. It also concentrates on system call interface efficiency, and especially read() system call performance, the most used system call on most systems. IOCALL is intended for UNIX systems only.

RawIO - NEW
Low-level raw device benchmarking program written by Greg Lehey, the author of the book "The Complete FreeBSD", published by Walnut Creek. This benchmark will only compile under BSD as it uses BSD specific mmap() call. Port to Linux is currently in progress.

PostMark - NEW
A new benchmark to measure performance of e-mail, netnews, and e-commerce classes of applications. PostMark was created to simulate heavy small-file system loads with a minimal amount of software and configuration effort and to provide complete reproducibility. It can be compiled under Solaris, Digital Unix, and Win32 environments. Learn more about the PostMark and download the source code by following the link above.


Windows NT/2000/2003/XP
Nbench
A very nice little benchmarking program for Windows NT. Nbench reports the following components of performance:
  • CPU speed: integer and floating operations/sec
  • L1 and L2 cache speeds: MB/sec
  • main memory speed: MB/sec
  • disk read and write speeds: MB/sec
SMP systems and multi-tasking OS efficiency can be tested using up to 20 separate threads of execution.

NTiogen 1.03 - UPDATED
NTiogen benchmark was written by Symbios Logic. It's Windows NT port of their popular UNIX benchmark IOGEN. NTIOGEN is the parent processes that spawns the specified number of IOGEN processes that actually do the I/O.

The program will display as output the number of processes, the average response time, the number of I/O operations per second, and the number of KBytes per second.

IOmeter - UPDATED
This benchmark was originally written by Intel. Intel has discontinued the development and released the source code into public domain. SOURCEFORGE.NET is currently hosting this project. IOMETER is a disk I/O subsystem measurement and characterization tool for single and clustered systems. Iometer does for a computer's I/O subsystem what a dynamometer does for an engine: it measures performance under a controlled load. It is now available for Windows 2000, Linux, and Solaris.

Bench32
A very comprehensive benchmark that measures overall system performance under Windows NT or Windows 95. Unfortunately, the company that wrote this benchmarking program seems to have gone out of business. You can find a local copy of Bench32 v.1.21 here.

ThreadMark
A very popular benchmark written by Adaptec. Adaptec's decided that they cannot support it anymore and thus they have removed this benchmark from their web site. Click on the link to download ThreadMark from our server.

HDTach v.2.61
Shareware/commercial disk I/O benchmark. HD Tach is a physical performance hard drive test for Windows 95/98 and Windows NT. In Windows 95/98 it uses a special kernel mode VXD to get maximum accuracy by bypassing the file system. A similar mechanism is used in Windows NT. HD Tach reads from areas all over the hard drive and reports its average speed. It also logs the read speeds to a text file that you can load into a spreadsheet and graph to visually read the results of the test.


DOS Benchmarks
SCSITool - NEW
A very comprehensive diagnostics and benchmarking tool for SCSI storage devices. Currently supported device types are: harddisk, tape, cd-rom, optical and removable disks. Learn more about the SCSITool and download the program by following the link above.

RAIDmark
The only benchmark we have found that was specifically created to measure the performance of RAID arrays. RAIDmark benchmarking program by DynaTek Automation Systems Inc., measures cache size, system overhead, and application-level performance. Includes MS-DOS and Novell versions. Unfortunately, the source code is not included. As far as we know, this was the last release of RAIDmark; DynaTek no longer supports or does any development of this benchmarking program.

Qbench
DOS hard disk benchmark from Quantum Corporation which measures data access time and data transfer rate. Just a nice little benchmark for quick results. No source code included.

COREtest
DOS disk benchmarking program created by CORE International. CORE Disk Performance Benchmark is distributed as a DOS binary, no source code included.

Wednesday, July 23, 2008

Tuesday, July 22, 2008

Random

C Library random function: rand() output is a 15-bit random number

int bigrand() // a 30 bits random variable
{
return RAND_MAX * rand() + rand();
}

return a random number from the range l to u

int rand(int l, int u)
{
return l + bigrand() % (u-l+1);
}

---------------------------

select with probability 2/5

bigrand() % 5 <>;

select m out of n number:

select = m
remaining = n
for i = [0, n)
******if (bigrand() % remaining ) < select
***********print i
***********select--
******remaining--

Q: Write m sorted integers random from 0...n-1

Solution-1: randomly select one number from 0 to n-1 for m times, and then sort this m element array.

Solution-2: "Shuffle card".

for i = [0, n-1)
{
swap(i, randint(i, n-1));
}



Q: read a text file and output each line randomly on the fly

always select the first line, select the second line with probability one half, the third line with probability one third and so on.

Monday, July 14, 2008

Namespace

1. The definition of namespace does not have to be continuous and can even span different program text files, which could help us to organize the library into interfaces and implementations.

2. Scope operators can also be used to refer to members of the global namespace. Global namespace does not have a name. ::name_in_the_globalspace

3. A nested namespace is a nested scope within the namespace that contains it. And during name resolution, nested namespace behave similarly to nested blocks. An entity declared in an enclosing namespace is hidden by an entity of the same name declared in a nested namespace. Silmiarly, an entity declared in a namespace is hidden by an entity declared in local scope.

4. Unnamed namespace is used to declare an entity locale to a file and never spans multiple text files. It is not necessary to use scope operator to refer to members of unnamed namespaces. In C, a global static is invisible outside of the file in which it is declared.

5. Namespace aliases
namespace IBM_1 = International_Business_Machines
namespace IBM_2 = International_Business_Machines

6. A name introduced by a using declaration has these characteristics:
6.1. It must be unique in its scope
6.2. It hides the same name introduced by a declaration in an enclosing scope
6.3. It is hidden by a declaration of the same name in a nested scope

Friday, July 11, 2008

Effective C++

Item 11: Declare a copy constructor and an assignment operator for classes with dynamically allocated memory, which means you probably have pointers in your class.

copy constructor is used to initialize a new created object and assignment is used to initialize an already existing object.

Tricky: if you do not want others to use copy constructor and assignment operator, then just declare the functions but do not define them at all. Generally those two are enabled/disabled together.

Item 27: Explicitly disallow use of implicitly generated member functions you don't want.

Just make the functions private may not be enough, member and friend functions still can call them. But if we just declare them without definition, we will get link-time error when we try to invoke any of them.

Item 44: Say what you mean; understand what you're saying

public inheritance = isa
nonvirtual member function means invariance over specialization.

Item 45: Know what functions C++ silently writes and calls

class Empty {} is equal to
class Empty
{
Empty();
~Empty();
Empty(const Empty& rhs); //copy constructor
Empty& operator=(const Empty &); //assignment operator
Empty* operator&();
const Empty* operator&() const;
};

The compiler generated destructor is nonvirtual unless it's for a class inheriting from a base class that itself declares a virtual destructor.

c++ will refuse to generate the assignment operator for you if your class contain reference or const members. (if you think of the behaviors of assignment operator, you will see the reason)
Also c++ will refuse to generate the assignment operator for derived classes that inherit from base classes declaring the standard assignment operator private.

Item 14: Make sure base classes have virtual destructors

When you try to delete a derived class object through a base class pointer and the base class has a nonvirtual destructor, the results are undefined.

If a class does not contain any virtual functions, that is often an indication that it is not mean to be used as a base class. When a class is not intended to be used as a base class, making the destructor virtual is usually a bad idea.

One rule is declaring a virtual destructor in a class if and only if that class contains at least one virtual function. Also declare a pure virtual destructor in the class you want to be abstract. One twist: you must provide a definition for the pure virtual destructor, because this virtual destructor will definitely be called by the derived class's destructor.

Item 15: Have operator= return a reference to *this

C& C::operator=(const C &);

The return type of operator= must be acceptable as an input to the function itself, otherwise, it will prevent chains of assignments.

If we remove the const qualifier, it will prevent implicit type conversion. const-correctness: it's never legal to pass a const object to a function that fails to declare the corresponding parameter const.

Item16: Assign to all data members in operator=

Derived& Derived::operator=(const Derived & rhs)
{
if (this == &rhs) return * this;
Base::operator=(rhs); //make an explicit call to base class assignment operator= function
//*this will be still be the implicit left-hand object, just like calls to member functions within //other member functions.
y = rhs.y; // assign to data members defined in derived class
return *this;
}

One nastiest bugs in all c++-dom: it fails to copy the base class part when a derived object is copy constructed. To avoid this problem, derived's copy constructor must make sure that the Base's copy constructor is invoked instead of Base's default constructor. Just be sure to specify an initializer value for Base in the member initialization list of derived's copy constructor.

class Derived: public Base
{
//Base(rhs) will invoke base copy constructor
Derived(const Derived & rhs): Base(rhs), y(rhs.y) { }
}

Item17: Check for assignment to self in operator=

Aliasing: having two or more names for the same underlying object.
Object identity: 1) if the objects have the same value or 2) if the objects have the same address in memory or 3) write your own identity function and provide operator==.

Anytime you write a function in which aliasing could conceivably be present, you must take that possibility into account when you write the code.

Item 19: Understand the origin of temporary objects

True temporary objects in C++ are invisible and arise whenever a non-heap object is created but not named. Unnamed objects arise in one of the two situations: 1) when functions return objects and 2) when implicit type conversions are applied to make function calls succeed, these conversions occurs only when passing objects by value or when passing to a reference-to-const parameter.

Learn to look for such constructs, and your insight into the cost of "behind the scenes" compiler actions will markedly improve.

Item 20: Avoid data members in the public interface

Hide all your data members behind a wall of functional abstraction. If you implement access to a data member through a function, you can later replace the data member with a computation, and nobody using your class will be any the wiser.

Item 21: Use const whenever possible

1. Outside of classes, use it for global or namespace constants

const A * c = new A();
A* e = c;
This is wrong

A* const c = new A();
A* e = c;
This is right

2. Outside of classes, use it for static objects (local to a file or a block)

3. Inside of classes, use it for both static and nonstatic data members

const nonstatic data members are const to each independent class objects. If you want to have const data for the class, use enum. enum will not take objects' space and replaced during compilation time.

const members may only be initialized and must be initialized via initializer list, NEVER assigned. Also all the consturctors should initialize the const data members in their initializer list!

But how about const static?

4. For pointers, const char * const p = "hello";

5. Within a function declaration, const can refer to the function's return value, to individual parameters.

const int & foo (const int para) { }

6. For member functions, to the function as a whole.

6.1) Member functions differ only in their constness can be overloaded. The class object's constness decides which function will be invoked. const is part of the function signature, which mean you have to put const both in the class declaration and function definition if the definition is out of class body.
6.2) const member function can ONLY be called by const class object
6.3) constructor and destructor are exceptions and const class object could call constructor/destructor even they are not const.
6.4) a class object is constant after constructor and before destructor.

7. Mutable

bitwise constness vs conceptual constness (which shows constness only to the clients)

When applied to nonstatic data members, mutable frees those members from the constraints of bitwise constness. Mutable data members can NEVER be const, even the data members are in a const class object. Mutable data members can ALWAYS be updated, even in the const member function.

8. volatile
objects may be modified out of compiler's control, such as I/O interface data structure. Similar to const, volatile object can only invoke volatile member function, constructor and destructor.

Item 12: Prefer initialization to assignment in constructors

Construction of objects proceeds in two phases:
1. Initialization of data members
2. Execution of the body of the constructor that was called

Initialization is more efficient. We only need to call copy constructor for the data members if we use initialization list. But we have to call both default constructor and assignment operator= for the data member if we use assignment in constructors.

const and reference member can ONLY be initialized, NEVER assigned. So if we stick to initialization, we don't need to change initialization code if we later change some members to const or reference.

Item 13: List members in an initialization list in the order in which they are declared.

Rule: class members are initialized in the order of their declaration in the class. destructors for the members of an object are always called in the inverse order of their constructors. So in this way, compiler does not to keep track of the order in which the members were intialized for each object.

Only nonstatic data members are initialized according to the rule. Static data members act like global and namespace objects, so they are intialized only once.

Item 6: Use delete on pointer members in destructors

Adding a pointer member almost always requires each of the following:
1. Initialization of the pointer in EACH of the constructors. If no memory is to be allocated to the pointer in a particular constructor, the pointer should be initialized to 0.
2. Deletion of the existing memory and assignment of new memory in the assignment operator
3. Deletion of the pointer in the destructor

Item 22: Prefer pass-by-reference to pass-by-value

Pass by value: Function parameters are initialized with COPIES of the actual arguments, and function callers get back a COPY of the value returned by the function.

The meaning of passing an object by value is defined by the copy constructor of that object's class.

Pass-by-reference also avoids what is called the "slicing problem". When a derived class object is passed as a base class object, all the specialized features that make it behave like a derived class are "sliced" off, and you're left with a simple base class object, and you are left with a simple base class.

Item 23: Don't try to return a reference when you must return an object

const Rational operator*(const Rational & lhs, const Rational &rhs) { }

We can NOT return reference for the above function.

A function can only create a new object in only two ways: on the stack or on the heap. A reference is just a name, a name for some existing object.

Rational w, a, b, c;
w = a*b*c; //if we return references (to object created inside the function), memory leak

Item 29: Avoid returning "handles" to internal data

The lifetime of the temporary object returned from function will be until the end of the expression containing the call.

For const member functions, returning handles is ill-advised, because it violates abstraction. Even for non-const member functions, however, returning handles can lead to trouble, especially when temporary objects get involved. We should avoid dangling handles as we avoid dangling pointers.

Item 28: Partition the global namespace

A namespace is just a fancy way of letting you use the prefixes you know and love without making people look at them all the time.

Access symbols in namespace in any of the three ways:
1. importing all the symbols in a namespace into a scope: using namespace std;
2. importing individual symbols into a scope: using std::cout;
3. explicitly qualifying a symbol for one-time use: std::cout << "hello world!"; One of the nicest things about namespace is that potential ambiguity is not an error, provided you never refer to the conflict symbols.

Item 26: Guard again potential ambiguity

C++ Philosophy: potential ambiguity is not an error.

Access restrictions are not taken into account when disambiguating references to multiply inherited members. Becuase changing the accessibility of a class member should never change the meaning of a program.

Item 30: Avoid member functions that return non-const pointers or references to members less accessible than themselves.

You won't want to sacrifice the access restrictions that private and protected afford you. Use const whenever possible.

Item 31: Never return a reference to a local object or to a dereferenced pointer initialized by new within the function.

1. reference to non-existing object, which is undefined.
2. cause memory leak

Item 32: Postpone variable definitions as long as possible

In this way, you avoid not only constructing and destructing unneeded objects, you also avoid pointless default constructions. Define and initialize via copy constructor will make the meaning more clear.

Item 38: Never redefine an inherited default parameter value

Virtual functions are dynamically bound, but default parameter values are statically bound.

An object's static type is the type you declare it to have in the program text. An ojbect's dynamic type is determined by the type of the object to which it currently refers.

Item 37: Never redefine an inherited nonvirtual function

Nonvirtual functions are statically bound. Which nonvirtual function to call is decided by the declared type of the pointer.

class B { void f(); }
class D: public B {void f();}
B b;
D d;
B * pB = &b;
pB-> f();//call B::f()
pB = &d;
pB->f(); //call B::f()

Item 24: Choose carefully between function overloading and parameter defaulting

In general, if you can choose a reasonable default value and you want to employ only a single algorithm, you'll use default parameters.

You have to use overloaded functions if the algorithms depend on the input.

Using overloaded functions that call a common underlying function for some of their work to avoid code duplication.

Item 19: Differentiate among member functions, non-member functions, and friend functions

Virtual functions must be members. Non-member function can NOT be virtual. And if a function has to be dynamically bound, you've got to use a virtual function, a member of some class.

Operator >> and operator << style="font-weight: bold;">parameter list
, never for the object on which a member function is invoked. In addition, if the function needs to access non-public members, make it a friend.

Everything else should be a member function.

Item 33: Use inlining judiciously

Inline is a hint, not a command.

Initially, don't inline anything, or at least limit your inlining to those functions that are truly trivial.

80-20, a typical program spends 80 percent of its time executing only 20 percent of its code. It's an important rule, because it reminds you that your goal as a software developer is to identify the 20 percent of your code that is actually capable of increasing your program's overall performance.

It's all wasted effort unless you're focusing on the right functions.

Item 39: Avoid casts down the inheritance hierarchy

Try to use virtual functions instead of if-then-else style of programmings that downcast objects.