2010/03/14

Python 简明学习笔记(二)

六:函数

函数是重用的字符串.
函数的定义通过关键词 def

def <函数名>():
<函数体>

函数的形参:参数在函数定义的圆括号内指定,用逗号分隔。
函数的实参:调用函数时,按照形参的格式交由函数处理的数据叫做实参。

eg:
#!/usr/bin/python
#Filename: func_param.py

def printMax(a,b):
    if a>b:
        print a
    else:
        print b

printMax(3,4)

局部变量:没有特殊声明,在函数内定义的变量都是局部变量,其作用域始于定义处,终止于函数结尾。

使用global语句:将变量生命为全局变量。
eg:

#!/usr/bin/python
#Filename:func_global.py
a=10
def func():
    global x
    print 'x=',x
    x=2
    print'changed local x to ',x
    a=20
    print 'a in the func is',a

x=50
print 'a in the outer is ',a
func()
print 'value of a is',a
pirnt 'value of x is ',x

output:
a in the outer is 10
x=50
changed local x to 2
value of a is 10
value of x is 2

默认参数值:对于一些函数,希望它的一些参数是可选的,如果用户互相为这类参数提供值的话,这些参数使用默认值。

eg:
#!/usr/bin/python
#Filename:func_default.py

def say(message,times=1):
    print message*times

say ('hello')
say ('world',5)

output:
hello
worldworldworldworldworld

关键参数:一个函数有多个参数,作者只想指定其中一部分,那么作者可以通过命名来为这些参数赋值,这些参数被称为关键参数,用户用名字(关键字)而不是闻之来给参数指定实参。
eg:

#!/usr/bin/python
#Filename:func_key.py

def func(a,b=5,c=10)
    print'a =',a,'b=',b,'c=',c

func(1)
func(2,c=30)
func(c=40,a=3)

output:
a=1,b=5,c=10
a=2,b=5,c=30
a=3,b=5,c=40

return语句:return语句用来从一个函数返回,即跳出函数。
eg:
#!/usr/bin/python
#Filename:func_return.py

def maxnum(x,y):
    if x>y:
        return x
    else:
        return y

print maxnum(2,3)


DocStrings,文档字符串:有点像javadoc

#!/usr/bin/python
# Filename: func_doc.py

def printMax(x, y):
'''Prints the maximum of two numbers.
The two values must be integers.'''
    x = int(x) # convert to integers, if possible
    y = int(y)
    if x > y:
        print x, 'is maximum'
    else:
        print y, 'is maximum'

printMax(3, 5)
print printMax.__doc__  #双下划线,Python中的
            #help()命令其实就是抓取程序的__doc__属性

output:
$ python func_doc.py
5 is maximum
Prints the maximum of two numbers.
The two values must be integers.



七:模块
模块基本上是一个包含了所有你定义的函数和变量的文件。模块文件必须以.py为扩展名。
模块可以从其他程序调入,以便利用它的功能。这也是我们使用Python标准库的方法。

#!/usr/bin/python
#Filename:using_sys.py

import sys

print 'the command line arguments are:'
for i in sys.argv:
    print i

print'\n\n the pythonpath is :\n',sys.path,'\n'


output:
$python using_sys.py we are arguments
the command line arguments are:
using_sys.py
we
are
arguments
the pythonpath is :
['/home/swaroop/byte/code', '/usr/lib/python23.zip',
'/usr/lib/python2.3', '/usr/lib/python2.3/plat-linux2',
'/usr/lib/python2.3/lib-tk', '/usr/lib/python2.3/lib-dynload',
'/usr/lib/python2.3/site-packages', '/usr/lib/python2.3/site-packages/gtk-2.0']

#字节编译的.pyc文件:程序处理一个模块比较耗费资源,如果将模块编译成字节码的.pyc为扩展名的文件,效率将大大提高。这些字节码也是与平台无关的。

#from...import语句:
如果你想要直接输入argv变量到你的程序中(避免在每次使用它时打sys.),那么你可以使用from sys import argv语句。如果你想要输入所有sys模块使用的名字,那么你可以使用from sys import *语句。这对于所有模块都适用。一般说来,应该避免使用from..import而使用import语句,因为这样可以使你的程序更加易读,也可以避免名称的冲突。

模块的__name__属性:模块的名字
使用__name__属性的一种情况:当模块第一次被import时,这个模块的主模块就会被运行,假如我们只希望在程序被使用的时候运行模块,而不是在它被别动载入的时候,可以通过此属性完成。

#!/usr/bin/python
#Filename:using_name.py

if __name__=='__main__':
    print 'this program is being running by itself '
else:
    print:'i am bing imported from another module'

输出:
$python using_name.py
this program is being running by itself
$python
>>>imort using_name.py
i am bing imported from another module
>>>


创建用户模块:每个python程序都是一个模块
eg:
#!/usr/bin/python
#Filename:mymodule.py

def sayhello():
    print'hello ,this is mymodule speaking.'
version='0.1'
#end of mymodule.py
#注意:此模块需要被放置在import它程序的同一目录,或放在sys.path中。

#!/usr/bin/python
#Filename:using_mymodule.py

import mymodule
mymodule.sayhello()
print 'version:' ,mymodule.version

output:
hello ,this is mymodule speaking
version:0.1



dir()函数:内建函数,列出模块定于的标识符(包含函数.类.变量等)
eg:
$python
>>>import sys
>>> dir (sys) #get list of attributes of sys module
.....
>>>dir() #get list of attributes of current module
.....
>>>a=5 #create a new variable 'a'
>>>dir()
.....
['__builtins__', '__doc__', '__name__', 'a', 'sys']
>>>del a #delete/remove a name
>>>dir()
.....
>>>


八:解决问题:python脚本

备份脚本 version 1:

#!/usr/bin/python
#Filename:backup_ver1.py

import os
import time

#the files and dirs that you wanna to backup
#if you are using windows,use source=[r'c:\documents',r'd:\dev']
source=['/home/anix/document','/etc/','/usr/bin/']

#the directory that the backup files are stored
target_dir='/media/backup/'

#the name of the backup archieve
target=target_dir+os.sep+time.strftime(%Y%m%d%H%M%S')+'.tar.gz'

#the command string
tar_command="tar -cvzf %s %s"%(target,''.join(source))

#run the script
if os.system(tar_command)==0:
    print'successful backup to',target
else:
    print'backup failed'




#!/usr/bin/python
#Filename:backup_ver2.py

import os
import time

source=['/home/anix','/etc/']
target_dir='/media/backup'
today=target_dir+time.strftime('%Y%m%d')
now=time.strftime('%H%M%S')

if not os.path.exists(today):
    os.mkdir(today)
    print'successfully created directory',today
target=today+os.sep+now+'.tar.gz'

tar_command='tar cvzf %s %s' %(target,''.join(source))

if os.system(tar_command)==0:
    print'successful backup to ',target
else:
    print'backup failed'


软件开发过程:分析->设计->编写->测试->使用->维护(优化)

Python 简明学习笔记(一)

               Python 简明学习笔记

一:最初的步骤:
    ・添加环境变量:path=%path%;c:\python26;.
    ・第一个helloworld程序:
    #!/usr/bin/python
    #Filename:hellowrold.py
    pirnt 'hello world'
   
    运行:Python helloworld.py
    输出:hello world


二:基本概念:

常量:不能改变值的量
数:
    整数:int
    长整数:long //int和long 有合并的趋势,长整形所表达的数的最大值取决于用户计算机的虚拟内存总数,与java中的bigInterger相似。
    浮点数:float 如:2.23E-4
    复数: -5+3j
    decimal:用于十进制浮点数。并非内建,使用前需导入decimal模块。例如:由于二进制表示中有一个无限循环片段,数字1.1无法用二进制浮点数精确表示,如:
        >>>1.1
        1.1000000000000000000001
        >>>print decimal.Decimal('1.1')
        1.1


字符串:string
    ・使用单引号('')
      引号中的所有空白都原样保留,如'this is a python example'
    ・使用双引号("")
      同单引号。
    ・使用三引号('''或""")
      用于指示一个多行字符串,在其中可以自由使用'和":
    '''example of multi-line string.
    "what is your name ?"
    'my name is anix.'
    '''
    ・转义符:(\)
      如:'what\'s your name?' //注意这里也可以用双引号而不使用转义符:"what's your name?"
      又如:"this is the first sentence.\
        this is the second one."等价于"this is the first sentence.this is the second one."
    ・自然字符串:如果需要指定某些不需要如转义符那样的特别处理字符串,那么需要指定为自然字符串,自然字符串通过给字符串加上前缀r或R指定:如:
        r 'newlines are indicated by \n'
    ・Unicode字符串
    字符串中包含非拉丁字母时,需要被指定为Unicode字符串,制定方法为在字符串前加上前缀U或u,如:U"这是简体中文。"
    ・星号*
      表示重复,如:
        >>>pystr='hello'
        >>>pystr * 2
        hellohello
        >>>'-'*10
        '----------'
tips:字符串是不可变的。

变量
标示符的命名:
    ・标示符的第一个字符必须是字母表中的字母或一个下划线'_'
    ・标示符其他部分可以由字母,下划线,数字组成。
    ・标示符对大小写敏感。

数据类型:变量可以处理的不同类型的值称为数据类型
对象

三:运算符与表达式

运算符        说明        例子
+                3+5得8.'a'+'b'得'ab'
-
*                2*3得6;'ha'*3得'hahaha'
**        返回x的y次幂    2**10得 1024
/                4/3得1;4.0/3得1.333333
//        取整        4/3.0得1.0
%        取模        4//3.0得1;8%3得2;-25.5%2.25得0.75

<<        左移        2<<1得4
>>        右移        2>>1得1;3>>1得1
&        按位与
|        按位或       
^        按位非
~        按位翻转(x的按位翻转式-(x+1)) ~5得-6
<
>
<=
>=
==
!=
not        布尔非
and        布尔与
or        布尔或

运算符优先级:

运算符         描述
lambda         Lambda表达式
or         布尔“或”
and         布尔“与”
not x         布尔“非”
in,not in     成员测试
is,is not     同一性测试
<,<=,>,>=,!=,==    比较
|         按位或
^         按位异或
&         按位与
<<,>>         移位
+,-         加法与减法
*,/,%        乘法、除法与取余
+x,-x         正负号
~x         按位翻转
**         指数
x.attribute     属性参考
x[index]     下标
x[index:index]     寻址段
f(arguments...)     函数调用
(experession,...)     绑定或元组显示
[expression,...]     列表显示
{key:datum,...}     字典显示
'expression,...'     字符串转换

四:数据结构

1:list tuple
列表和元组可以被看做是数组,可以存储任意类型数据,并可以用切片操作[],[:]得到子集。
区别是:1:列表用[]包裹,元组用()包裹;2:列表元素可以修改,而元组数据不可以修改。
>>>alist=[1,2,3,4]
>>>alist
[1,2,3,4]
>>>alist[0]
1
>>>alist[2:] #从第三个元素开始到结尾(包括第三个)
[3,4]
>>>alist[:3] #从头到第四个元素(不包括第四个)
[1,2,3]
>>>alist[0]=5
>>>alist
[5,2,3,4]

>>>atuple=('apple',3,7,'orange')
>>>atuple
('apple',3,7,'orange')
>>>atuple[:3]
('apple',3,7)
>>>atuple[2:]
(7,'orange')
>>>atuple[1:3]
(3,7)


2:字典 map
工作原理类似哈希表,是由key-value对组成,用{}包裹,key和value之间用':'分割,不同key-value对之间用','分割。

>>>adict={'host':'google.com','dns':'8.8.8.8'}
>>>adict['port']=23
>>>adict
{'host':'google.com','dns':'8.8.8.8','port':23}
>>>adict['host']
'google.com'
>>>adict.keys()
['host','dns','port']
>>>for key in adict:
   print key,adict[key]
```
host google.com
dns 8.8.8.8
port 23

3:序列

元组、列表和字符串都属于序列。序列的两个主要特点是:索引操作符和切片操作符。索引操作符可从序列中抓取一个特定项目,切片操作符可以从序列中获取一个子集。
Python中序列的一个重要特点是索引可以为负值:-1表示最后一个元素,,-2表示倒数第二个元素......
eg:

#!/usr/bin/python
# Filename: seq.py
shoplist = ['apple', 'mango', 'carrot', 'banana']
# Indexing or 'Subscription' operation
print 'Item 0 is', shoplist[0]
print 'Item 1 is', shoplist[1]
print 'Item 2 is', shoplist[2]
print 'Item 3 is', shoplist[3]
print 'Item -1 is', shoplist[-1]
print 'Item -2 is', shoplist[-2]
# Slicing on a list
print 'Item 1 to 3 is', shoplist[1:3]
print 'Item 2 to end is', shoplist[2:]
print 'Item 1 to -1 is', shoplist[1:-1]
print 'Item start to end is', shoplist[:]
# Slicing on a string
name = 'swaroop'
print 'characters 1 to 3 is', name[1:3]
print 'characters 2 to end is', name[2:]
print 'characters 1 to -1 is', name[1:-1]
print 'characters start to end is', name[:]

输出
$ python seq.py
Item 0 is apple
Item 1 is mango
Item 2 is carrot
Item 3 is banana
Item -1 is banana
Item -2 is carrot
Item 1 to 3 is ['mango', 'carrot']
Item 2 to end is ['carrot', 'banana']
Item 1 to -1 is ['mango', 'carrot']
Item start to end is ['apple', 'mango', 'carrot', 'banana']
characters 1 to 3 is wa
characters 2 to end is aroop
characters 1 to -1 is waroo
characters start to end is swaroop


4:引用
当在计算机中创建一个对象并把它赋予一个变量时,这个变量仅仅引用那个对象,而不是表示这个对象本身,两者只是存在绑定关系。还可以有其他变量指向同一个对象。

eg:

#!/usr/bin/python
#!Filename:reference.py

shoplist=['apple','mango','carrot','banana']
mylist=shoplist #mylist is just another name pointing
         to the same object
del shoplist[0]

print 'shoplist is ',shoplist
print 'mylist is ',mylist
#apple has been removed in the object, so the reference of it
#will print the same list which has no apple.

print'copy by making full slice'
mylist=shoplist[:]
del mylist[0] #remove first item


print 'shoplist is ',shoplist
print 'mylist is ',mylist

output:

shoplist is ['mango', 'carrot', 'banana']
mylist is ['mango', 'carrot', 'banana']
Copy by making a full slice
shoplist is ['mango', 'carrot', 'banana']
mylist is ['carrot', 'banana']

//列表的赋值语句不创建copy,你得通过切片创建拷贝。

五:控制流

1:if语句(if... elif...else:)
eg:
#!/usr/bin/python
#Filename:if.py

number=23
guess=raw_input('enter an integer:)

if guess==number:
    print'bingle!'
elif guess<number:
    print'a little higher~'
else:
    print'a little lower~'

print 'Done'

//Python中没有switch语句,你可以使用if...elif...else完成同样的工作,但在某些场合使用字典(map)会更有效率。

2:while语句

eg:
#!/usr/bin/python
#Filename:while.py

number=23
running=True

while running:
    guess=raw_input('enter an integer:')
   
    if guess==number:
        print r'bingle!\n'
        running=False
    elif guess<number:
        print r'a litter higher~\n'
    else:
        print r'a little lower~\n'

else:
    print'the loop is over~' #useless~
print'Done'

//你可以在while循环中使用一个else从句!

3:for循环
for...in 可以在一个递归对象上递归逐一使用队列的每个item。

eg:

#!/usr/bin/python
#Filename:for.py

for i in range(1,5): #等价于for i in【1,2,3,4】
    print i
else:
    print'loop is over'//useless

output:
1
2
3
4
loop is over

#range()是内建函数,产生一个序列。
#range(2,10,2),表明产生这么一个序列:从2开始,到10终止(不含10),步长为2 ,即【2,4,6,8】,如果没有第三个参数,默认步长为1.

#lese部分是可选的,如果包含else部分,它总是在for结束后执行一次,除非遇到break语句。
#for i in range(0,5)等价于C中 for(int i=0;i<5;++i)


4:break语句
中断/跳出循环
eg:

#!/usr/bin/python
#Filename:break.py

while True:
    s=raw_input()
    if s=='quit'
        break
    print'length of the string is ',len(s)
print 'Done'




5:continue

跳过当前循环的剩余语句,执行下一轮循环。

eg:

#!/usr/bin/python
# Filename: continue.py
while True:
s = raw_input('Enter something longer than 3 chars : ')
if s == 'quit':
break
if len(s) < 3:#len()为内建函数,返回字符串字长。
continue
print 'Input is of sufficient length'



#############################################
        G2
programming is fun
when the work is done
if you wanna make your work also fun:
    use Python!

#############################################

2010/03/13

The Revolution will be on YouTube

author:Gladio@phrack.org

Forget everything you know about revolutions. It's all wrong.

Fighting a conventional war in an industrialized nation is suicide. Even
if you could field a military force capable of defeating the government
forces, the wreckage wouldn't be worth having. Think about mortar shells
landing in chemical plants. Massive toxic waste spills. Poisonous clouds
drifting with the winds. Fighting a war in your own backyard is just
plain stupid. Notice how the super-powers fight each other with proxy
wars in other countries.

Sure it might be fun to form a militia and go play army with your friends
in Idaho. Got some full-auto assault rifles? Maybe even mortars, heavy
machine guns and some anti-aircraft guns?

Think they can take out an AC-130 lobbing artillery shells from 12 miles
away? A flight of A-10s spitting depleted uranium shells the size of your
fist at a rate that makes the cannon sound like a redlined dirt bike? A
shooting war with a modern government is a shortcut to obliteration.

Most coups are accomplished (or thwarted) by skillful manipulation of
information. There have been a number of countries where tyrants (and
legitimate leaders) have been overthrown by very small groups using mass
communications effectively.

The typical method involves blocking all (or most) information sources
controlled by the government, and supplying an alternative that delivers
your message. Usually, you just announce the change in government, tell
everyone they are safe and impose a curfew for a short time to consolidate
your control. Announce that the country, the police and the military are
under your control, and keep repeating it. Saturate the airwaves with your
message, while preventing any contradictory messages from propagation.

Virtually all broadcast media use the telephone network to deliver content
from their studios to their transmitters. Networks use satellites and
pstn to distribute content to local stations, which then use pstn to
deliver it to the transmitter site.

Hijacking these phone connections accomplishes both goals, of denying the
'official' media access, and putting your own message out.

In cases where you can't hijack the transmitters, dropping the pstn
will be effective. Police and military also use pstn to connect dispatch
centers with transmitter towers. Recently, many have installed wireless
(microwave) fallback systems.

Physically shutting down the pstn just prior to your broadcasts may be
very effective. This is most easily accomplished by physical damage to
the telco facilities, but there are also non-physical technical means to
do this on a broad scale. Spelling them out here would only result in the
holes being closed, but if you have people with the skill set to do this,
it is preferable to physical means because you will have the advantage
of utilizing these communications resources as your plan progresses.


Leveraging the Internet

Most of the FUD produced about insurgence and the internet is focused on
"taking down" the internet. That's probably not the most effective use
of technical assets. An insurgency would benefit more from utilizing the
net. One use is mass communications. Get your message out to the masses
and recruit new members.

Another use is for communications within your group. This is where things
get sticky. Most governments have the ability to monitor and intercept
their citizen's internet traffic. The governments most deserving of
being overthrown are probably also the most effective at electronic
surveillance.

The gov will also infiltrate your group, so forums aren't going to
be the best means of communicating strategies and tactics. Forums can
be useful for broad discussions, such as mission statements, goals and
recruiting. Be wary of traffic analysis and sniffing. TOR can be useful,
particularly if your server is accessible only on TOR network.

Encryption is your best friend, but can also be your worst enemy. Keep
in mind that encryption only buys you time. A good, solid cipher will
not likely be read in real time by your opponent, but will eventually
be cracked. The important factor here is that it not be cracked until
it's too late to be useful.

A one time pad (OTP) is the best way to go. Generate random data and
write it to 2, and only 2, DVDs. Physically transport the DVDs to each
communications endpoint. Never let them out of your direct control. Do
not mail them. Do not send keys over ssh or ssl. Physically hand the DVD
to your counterpart on the other end. Never re-use a portion of the key.

Below is a good way to utilize your OTP:

Generate a good OTP (K), come up with a suspicious alternate message
(M), and knowing your secret text (P), you calculate (where "+" = mod
26 addition):

K' = M + K
K'' = P + K
C = K' + P

Lock up K'' in a safety deposit box, and hide k' in some other off
site, secure location. Keep C around with big "beware of Crypto systems"
signs. When the rubber hose is broken out, take at least 2 good lickings,
and then give up the key to the safety deposit box. They get K'',
and calculate

K'' + C = M

thus giving them the bogus message, and protecting your real text.


Operational Security

The classic "cellular" configuration is the most secure against
infiltration and compromise. A typical cell should have no more than 5-10
members. One leader, 2 members who each know how to contact one member
of an 'upstream' cell, and 2 members who each know how to contact one
member of a downstream cell. Nobody, including the leader, should know
how to contact more than one person outside of their own cell.

Never use your real name, and never use your organizational alias in
any other context.

Electronic communications between members should be kept to a
minimum. When it is necessary, it should only be conducted via the OTP
cipher. Preferably, these communications should consist of not much more
than arranging a physical meeting. Meet at a pre-arranged place, and
then go to another, un-announced place where surveillance is difficult,
to discuss operational matters.

Do not carry a phone. Even a phone which is switched off can be
tracked, and most can be used to eavesdrop on discussions even when
powered down. Removing the battery is only marginally safer, because
tracking/listening gear can be built into the battery pack. If you find
yourself stuck with a phone during a meeting, remove the battery and
place both the phone and battery in a metal box and remove it from the
immediate area of conversation.

It never hurts to generate some bogus traffic. Gibberish, random data,
innocuous stories etc., all serve to generate noise in which to better
hide your real communications.

Steganography can be useful when combined with solid crypto. Encrypt and
stego small messages into something like a full length movie avi, and
distribute it to many people via a torrent. Only your intended recipient
will have the key to decrypt the stegged message. Be sure to stego some
purely random noise into other movies, and torrent them as well.

Hopefully you'll find this document useful as a starting point for
further discussion and refinement. It's not meant to be definitive, and
is surely not comprehensive. Feel free to copy, add, edit or change as
you see fit. Please do add more relative to your area(s) of expertise.

2010/02/17

ssh代理的架设


step1:设置sshd
编辑/etc/ssh/sshd_conf配置文件,增加下面的命令:
AllowTcpForwarding yes
重启sshd

step2:设置apache
编辑 /etc/httpd/httpd.conf配置文件,进行以下修改:
Listen 127.0.0.1:8080
LoadModule proxy_module /usr/lib/apache/modules/libproxy.so
#取消注释即可,库文件名称可能会随版本变化而变化。


ProxyRequests On
AllowCONNECT 443 5050 5190
#这里端口号为互联网服务所需要的端口,增加任何服务需要增加端口
#本例为SSL连接、AIM、yahoo IM。

Order deny,allow
deny from all
allow form 127.0.0.1

#只允许本地连接
ProxyVia On



重启apache

step3:配置客户端ssh
客户端需要在自己的.ssh目录新建一个文件,该文件包含你想要连接的主机的别名(alias),注意不要使用root作为用户名。
效果应该看起来如下所示:
~/.ssh/config

Host alias_for_somehost

HostName somehost.com (or an IP address)
User username
Compression yes
LocalForward 22 somehostontheothersideofthebastion:22
LocalForward 25 somemailserver:25
LocalForward 143 someimapserver:143
LocalForward 8080 127.0.0.1:8080

现在你只需要连接:
$ssh alias_for_somehost
password:
somehost$
注意:在使用代理时必须保证此会话为打开状态。

现在,你在本地~/.ssh/config中定义的端口都会走远程主机的端口。
现在,你可以使用8080端口浏览互联网信息,同样可以使用IM,只要确保端口被加入到了httpd.conf中的AllowCONNECT行。

2010/02/01

[翻译]寻你所爱

今天, 我很荣幸能来到你们中间,来到这个世界顶级大学的毕业典礼上。说实话, 我大学没有读完, 因此,此时此刻是我生命中距离大学毕业最近的一刻了。今天,我要为你们讲讲我生活中的三个故事。只是三个普通的故事而已。

第一个是关于我生活中的点点滴滴如何串连起来的故事。

当年,在Reed学院学习了六个月之后我就退学了, 但是在此之后我又再Reed学院呆了在十八个月,我为什么要退学呢?

这得从我出生时讲起。那时,我的亲生母亲,一名年轻的未婚大学毕业生, 决定让别人收养我。 由于她特别希望我的养父母也是大学毕业,所以,她安排好一切,使我能被一名律师和他的妻子所收养。但是她没有料到,当我出生之后,律师夫妇突然决定 — 他们想要一个女孩。所以,当时还在候补名单上的养父母, 突然在半夜接到了电话:“我们这儿有一个意外出生的的男婴,你们想收养他吗?”我的养父母回答道:“当然了!”。然而,我亲生母亲随后发现,我的养母大学没有毕业, 而我的养父甚至高中毕业都没有。于是她拒绝签收养合同。直到几个月后,当我的养父母保证将来一定会让我上大学之后,我亲生母亲的态度才软化。

十七年后,我真的上了大学。但是当时我无知选了一所学费几乎跟史丹佛大学一样贵的学院,学费花掉了我工薪阶层的父母的所有的积蓄。上学六个月后,我已经看不到其中的价值所在。我不知道我想要在生命中做什么,我也不知道大学能帮助我找到怎样的答案。而且,上学消耗了我父母的所有积蓄。所以,我决定休学。我相信生活一定有办法的。不能否认,我那时确实非常的害怕, 但是现在回头看看,那个决定确是我这一生中最棒的一个。从我退学的那一刻起, 我终于可以不必去读令我不感兴趣的课程了。我开始去修那些看起来有意思的课。

然而,这一切一点也不浪漫。我没有宿舍,我睡在朋友房间的地板上,我靠着回收五分钱的可乐罐子来买吃的。每周日晚上,我得走七英里路,穿过大半个镇,去Hare Krishna寺庙吃上一顿(免费的)不错的饭菜。我太爱吃那顿饭菜了。就这样,追寻着我的好奇与直觉,我跌跌撞撞走了过来。后来回头看看,这些经历都成了无价之宝。举例来说:

Reed学院在那时提供也许是全美最好的美术字课程。在整个校园内的每个海报, 每个抽屉的标签上面全都是漂亮的美术字。因为我休学了,可以不照正常选课程序来,所以我跑去学学怎样写出漂亮的美术字。我学到了san serif 和serif字体, 我学会了怎么样在不同的字母组合之中改变空格的长度, 还有怎么样才能作出最棒的印刷式样。那是一种科学永远不能捕捉到的、美丽的、真实的艺术精妙, 我发现那实在是太美妙了。

那时,我从来没有希望在一我这辈子中,能把这些学到的东西用在什么实处。但是十年之后, 当我们设计第一台麦金塔(Macintosh)电脑的时候,这些学到的都回来了:我们设计出了世界上第一台使用了漂亮的印刷字体的电脑。设想一下,如果我当年没有退学,那么我就不会上那个美术字课程, 那么麦金塔电脑就不会有这么多丰富的字体,以及赏心悦目的字体间距。而又因为微软Windows抄袭了麦金塔的,那么,现在没有任何的个人电脑会有这么美妙的字型了。当然,我在大学的时候,还不可能从点点滴滴中看到未来,但是,当我十年后回顾这一切的时候,真的豁然开朗了。

再次说明的是,你在向未来展望的时候不可能将这些点点滴滴串连起来;你只能在回顾过去的时候才可以做到。所以,你必须相信这些点点滴滴,会在你未来的某一天串连起来。你必须要相信某些东西:你的勇气、命运、生命、因缘。这种看问题的方法从来没有令我失望,它令我的人生整个不同起来。

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

我非常幸运。我在很早的时候就找到了我爱做的东西。我在二十岁的时候就和Woz在我父母的车库里面开创了苹果(Apple)公司。我们工作得很努力, 十年之后, 这个公司从那两个人发展到了超过四千名的雇员、价值超过二十亿的大公司。然而,我在刚刚三十岁的时候,我被炒了鱿鱼。而在此前一年,我们公司才发布了最好的产品:麦金塔电脑。你怎么可能被自己创立的公司炒了鱿鱼呢? 其实,在苹果公司快速成长的时候,我们雇用了一个我当时认为很有天分的人来和我一起管理公司。在最初的一年多, 公司运转的很好。但是后来我们对未来的看法发生了分歧, 最后只好分道扬镳。 董事会站在了他的那一边。所以,在三十岁的时候, 我被解雇了,并且是在公众面前把我解雇了。就这样,在而立之年,我生命的全部支柱消失了, 这对我真是毁灭性的打击。

在最初的几个月里,我真是不知道该做些什么。我觉得我令企业界的前辈们失望了 — 我把他们交给我的接力棒弄丢了。我和David Pack和Bob Boyce见面,并试图向他们道歉说我把事情搞得太砸了。我成了公众面前的十分负面的典型。我甚至想要离开硅谷。但是我渐渐发现了曙光 — 我仍然喜爱我从事过的东西。苹果公司发生的这些事情丝毫的没有改变这些, 一点也没有。我被驱逐了,但是我仍然钟爱它。所以我决定从头再来。

我当时没有觉察, 但是事后证明, 从苹果公司被炒是我这辈子发生的最棒的事情。因为,成功的沉重被从头来过的轻松所取代,每件事情都不那么确定。这让我觉得如此自由, 进入了我生命中最有创造力的一个阶段。

在接下来的五年里, 我创立了一个名叫NeXT的公司, 另一个叫Pixar的公司, 并且,我和后来成为我妻子的不可思议的女人相识。Pixar 创造了世界上第一个用电脑制作的动画电影——“玩具总动员”,现在他也是世界上最成功的动画制作工作室。而NeXT, 在一系列成功的运作后, 被苹果公司收购了: 我又回到了苹果公司。我们在NeXT发展的技术成了苹果电脑后来复兴的核心。另外,我和Laurence 一起建立了幸福的家庭.

我很确定,如果当年苹果电脑没开除我,这些事情一件也不会发生的。这副药很苦,可是我想作为病人我需要它。有些时候, 生活会拿起一块砖头向你的脑袋上猛拍一下 — 不要失去信心。我很清楚唯一使我一直走下去的,就是我做的事情令我无比钟爱。你需要去找到你所爱的东西。对于工作是如此, 对于你的爱人也是如此。你只有相信自己所做的是伟大的工作, 你才能真正得到满足。而唯一去做伟大的工作的方法是钟爱你所做的。如果你现在还没有找到你所爱的, 那么继续寻找、不要妥协。靠着你内心深处的指引, 当你找到她的时候,你就会知道你真的的找到了。就像任何很棒的关系一样, 随着岁月的流逝,你钟爱的工作只会越来越棒。所以要继续寻找,一直到你找到它,不要妥协!

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

当我十七岁的时候, 我读到了一句话:“如果你把每一天都当作生命中最后一天的话, 那么总有一天,你会发现它是正确的。”这句话给我留下了深刻的印象。从那时开始的过去三十三年里,我在每天早晨都会对着镜子问自己:“如果今天是我生命中的最后一天, 你会不会想完成你今天计划要做的事情呢?”当答案连续很多次是“不是”的时候, 我知道自己需要做些改变了。

“提醒自己即将死去” 是我在人生中下重大决定时,所用过的最重要工具。因为几乎所有的事情 –包括所有的外界期望,所有的荣誉与骄傲、所有对难堪和失败的恐惧–这些在死亡面前都会消失。留下的是真正重要的东西。 “提醒自己即将死去”是我知道的避免患得患失的思维误区最好办法。你已经没有比死亡更多可失去的了,因此, 你没有理由不去跟随自己的心一起跳动。

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

那是我最接近死亡的时候, 我还希望这也是未来的几十年中最接近的一次。从死亡线上又活了过来后, 我可以比之前死亡只是抽象概念时要更肯定告诉你们下面这些:   

没有人想死。即使那些想上天堂的人也不会为了上天堂而想死。但是死亡是我们每个人共同的终点,没有人逃得过。这是命中注定的,因为死亡简直就是生命中最棒的发明。是生命更新的使者,清除老人们,给新生代留下空间。现在你们是新生代,但是不久的将来,你们也会逐渐变老并被清除。抱歉讲得这么戏剧化,但是这是真的。

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

在我年轻时,有一本很棒的杂志叫做 Whole Earth Catalog,它是我们那一代人的宝典之一。杂志的发行人是Stewart Brand,他住在离这不远的Menlo Park,他把杂志办得很有诗意。那是1960年代末期,在个人电脑出现之前。所以这本书全部是用打字机、剪刀跟拍立得相机做出来的。杂志内容有点像印在纸上的谷歌(Google),而他在Google出现之前35年就有了。杂志是理想主义的,充满新奇工具与神奇的想法。

Stewart跟他的出版团队出了好几期Whole Earth Catalog,最终,他们推出了停刊号。那是在七十年代的中期,我正是你们现在这个年龄。在停刊号的封底是张清晨乡间小路的照片,小路是那种你很冒险才敢的走那种。在照片下有行小字:

保持饥饿,保持愚蠢。 (Stay Hungry. Stay Foolish. 又译求知若饥,虚心若愚, )

我总是希望自己能够那样。现在, 在你们即将毕业,开始新的旅程的时候, 我也希望你们能这样:

保持饥饿,保持愚蠢。

非常谢谢大家。

寻你所爱

今天我很荣幸能够在世界上最好的大学之一---斯坦福大学的毕业典礼上和你们共聚一堂,实话实说,我从来没从哪所大学毕业,这是我距离毕业典礼最近的一次。今天,我想给你们讲讲我生命中的三个故事,就这些,没什么大不了的,只不过是三个故事而已。

第一个故事是关于如何串联你生命中的经历。

我上了6个月学后就从雷德学院辍学了,但是在我真正离开雷德前在那里以一个辍学生的身份继续待了十八个月。但我为什么要退学呢?

从大学退学在我出生之前就已经埋下伏笔了。我的生母是一位年轻未婚的大学毕业生,她决定为我找一对养父母。她强烈的感觉我应该被一对大学毕业的夫妇收养,所以似乎一切都注定了我的养父母将会是一位法官和他的妻子。然而,在我出生后,他们在最后一刻决定他们真正想要的是一个女孩儿。所以我现在的父母——那时正在等候名单之列——在半夜接到了一个电话,:”我们有了一个意外的男婴,你们想要他吗?”他们说:“当然!”我的生母不久发现,我的母亲从没上过大学,而我的父亲甚至连高中都没有读完。她拒绝签署最后的领养协议。在僵持了几个月后,她终于同意签署协议了,我母亲也保证长大后我将接受高等教育。

17年后,我的确上了大学,但是我却天真地选择了一所学费几乎和斯坦福一样贵的大学,我工薪阶层的父母亲的薪水源源不断的被花费在我的学费上。六个月之后,我看不到大学教育的价值体现在什么地方,我不知道我今生到底想要干什么,更不晓得大学将如何将它们实现。在那里我正花费着我的父母一生攒下的财富。所以,我决定退学,并且相信会一切事情都会顺利。在当时看来,我的决定实在是很可怕了,但是从今天看来,那是我所做过的最正确的决定之一。我从退学的那一刻起,不必学习那些我不感兴趣的课程了,转而开始旁听那些真正吸引我的课。

那一点也不浪漫。我没有宿舍,因此我住在朋友寝室的地板上。我依靠回收可乐瓶获得的5分押金购买食物。每个周日晚上我会徒步走上七英里穿过镇子到寺庙去——因为在那里我可以吃上一顿好饭。饭菜不错,我很喜欢。就这样,追寻着自己的好奇与直觉,我跌跌撞撞走了过来。后来回顾那段时光,这些经历都成了无价之宝。举例来说吧:

雷德学院提供了或许是当时全国最好的书法教育。校园里的每一张海报、每一个标签都用书法很美丽的表达。因为我已经辍学了,所以我不必上规定的课程,我决定学习书法,学习他们是如何创造出如此奇妙的东西。我学习了“serif”和“san serif”字体——它们通过变换字母之间的空间来创造出伟大的书法。它们拥有一种用单纯的科学无法捕捉的美丽的、历史性的、艺术精妙。我发现他们是如此迷人。

我的书法技能在当时看来不会有任何实际的用处。但是十年之后,当我们设计第一台麦金托什机时,它们却给了我意外的回报。我们将那些美妙的字体设计进mac中,麦金托什机因而成为了人类历史上第一台拥有美丽字体的计算机。如果我在雷德没有上过书法课,mac或许永远不会拥有多样的打印机字样或是间隔恰当的字体。由于windows抄袭了mac,看来可能没有个人计算机能够拥有它们。如果我们有辍学的话,我永远也不会上书法课,个人电脑也就不会有现在它们有的美妙字体了。当然,在我上学时向前看串联起我的生活是不可能的,但是十年后在回望生活,又是如此的清晰。

在强调一下,当你向前看时你不能串联起你生活的点滴,你只能在回望时串联它们。因此,你必须相信你生活的点滴将会在你的未来被串联。你必须相信一些什么——你的直觉、你的命运、你的因缘•••无论相信那一种。这种方法从没有让我失望过,它成就了我生命中所有

的与众不同。

我的第二个故事是关于爱与失去。

我是幸运的,我很早就找到了我的真爱。在我20岁时,沃兹和我在我父母的车库中创立了苹果。我们努力工作,十年之后苹果从一家仅有我和沃兹两名员工在车库中创立的小作坊成长为一家市值二十亿圆有着四千名员工的企业。在发布了我们最好的产品——麦金托什机的一年之后,那年我三十岁,我却被解雇了。你也许会问:为什么我会被一家自己创立的公司解雇呢?那是因为随着苹果不断成长,我雇佣了一名我认为很有才能的人与我一同管理公司。在我们共事的头一年里,我们合作顺利。但是后来,我们对于公司的发展方向问题产生了分歧,最终我们只有分道扬镳了。董事会站在他的一边。所以我在三十岁时出局了,我成年生活的重心失去了,那是对我毁灭性的打击。

在那之后的几个月里,我一直无所事事。我感到自己让老一代的企业家失望了——我丢掉了传递到我手中的接力棒。我与大卫•帕卡德和鲍勃•努伊斯见了面,并向他们表示歉意,因为我把事情搞砸了。那时我是一个世人皆知的失败者,我甚至想过逃离硅谷。但是一些事情开始向我昭示:我依旧热爱自己的工作。在苹果的一系列变故一点也没有改变这一点。我被拒绝了,但是却依然深爱着自己的事业。因此,我决定重新开始。

当时我没有意识到,但是后来证明了被苹果解雇是在我身上发生的最好的事情。成功者的沉重负担被创业者的轻装上路所取代,未来的一切都是那么的不确定。自此我进入了生命中最具创造力的人生阶段。

在随后的五年里,我创立了两家公司,一家叫NeXT,另一家叫Pixar。并且与一个迷人的女人相爱,哪个人后来成为了我的妻子。Pixar继续制作世界上第一部电脑动画片——玩具总动员。现在Pixar已经成为世界上最成功的动画制作室。NeXT在一系列的成功运作后,被苹果公司收购了,我又回到了苹果。我们在NeXT上发展的技术现在已是帮助苹果复兴的核心。劳伦尼和我成立了一个幸福的家庭。

我确信,如果我没有离开苹果,这一切都不会发生。被苹果解雇是一副味道很苦的药,但是我认为病人需要它。有时候,生活对你迎头痛击,但是不要失去信念。我确信唯一支撑我一路走下去的就是我深深的爱着自己的事业。找到自己的真爱,对你的工作如此,对你的爱人依旧如此。你的工作将会占据你生命中的很大部分,唯一让自己真正满意的就是做自己认为伟大的事业,而做伟大事业的唯一方法就是做你深爱的工作。如果你还没有发现自己的真爱,继续寻找,不要妥协。用你心灵的指引,当你遇见她时,你会意识到的。正如一切伟大的关系,随着岁月的流逝,你与你的挚爱的关系会变的越来越好。所以,继续寻找,直到你找到她,永远也不要妥协。

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

当我十七岁时,我读过一句话:“如果你把每一天都当作自己生命中的最后一天的话,总有一天,会是正确的。”那句话给我留下了深刻的印象,从那时起的33年里,每天早晨我都会站在镜子前问自己:“如果今天是我生命中的最后一天,我愿意做我将要做的事情吗?”当答案连续很多次都是“不是”时,我知道自己需要改变点什么了。

提醒自己我将很快死去是我遇到的帮助自己做出生命中重大选择的最有效方法。因为几乎一切事情,一切不切实际的期望,一切骄傲,一切对尴尬和失败的恐惧在死亡面前都将褪色,剩下的只有真正重要的事情。提醒自己我将死去是我知道的最好方法来避免自己陷入患得患失的境地。你已经赤裸裸了,没有任何原因不去追随自己的心灵。

大约一年前,我被诊断为患了癌症。我在早上7点半做了一个检查,检查很清楚的显示在我的胰脏上有个肿瘤。那时我甚至还不知道胰脏是什么东西。医生告诉我那个肿块几乎肯定是一种不可治愈的癌症,我应该活不出半年。我的医生建议我回家打理好自己的事情,那是医生对临终病人的标准告诫。这意味着要设法在几个月里告诉你孩子本将要在下一个10年里告诉他们的事情;这意味着要确保自己的一切事情都处理妥当,不会给自己的家人制造麻烦;这意味着要说“再见”了。

我整天想着哪个诊断结果。那天晚上我做了个活组织切片检查。医生们将一个内窥镜通过我的喉咙穿过胃伸进肠子里,用探针刺进我的胰脏并从肿块上取下了一些细胞。我被麻醉了,但是我的妻子告诉我医生们通过显微镜检查了那些细胞后,惊喜的哭了起来。因为切片检查显示,那个肿块是是一种很罕见的,可以通过手术治愈的胰腺癌。我接受了手术,现在我康复了。

这是我和死亡最接近的一回。我也希望这次是在我今后的几十年里和死亡最接近的一回。经历了这次与死神擦肩而过的经历后,我可以较之以前死亡只是一个抽象的概念更加确定的告诉大家:

没有人愿意死去。甚至是渴望上天堂的人也不希望通过死亡来到达天堂。但是死亡是我们每个人生命的最终归宿。没有人曾经逃离这一宿命。死亡是人命中注定的,因为死亡或许是生命中最棒的发明。它是生命的更换机构,它清除老人,为新人让出地方。如今新人就是你们,但是在不太久的将来,你们也将渐渐变成老人继而被清除掉。抱歉说的如此直白,但是这却是真的。

你的生命是有限的,因此不要浪费它去过别人的生活,不要被由别人思考结果而订立的教条所羁绊,不要让别人的观点淹没自己心灵的声音。最重要的是:有勇气追寻自己的心灵与直觉,它们不知何故早已知道了你真正想要成为什么。其他的一切都是次要的。

在我年轻的时候,有一本神奇而富有诗意的出版物叫做《The Whole Earth Catalog》,那是我们那一代人的宝典。它的主编叫做•布兰德,就住在在离这里不远的门罗公园。那是上世纪六十年代末的事情,那时候个人电脑还没有发明,那本书是完全用打字机、剪刀和胶片相机完成的。书的内容有点象纸上的Google,而35年之后Google才问世。那套丛书是理想化的,充满着灵巧的工具和伟大的想法。

斯图尔特和他的团队制作了几卷的《The Whole Earth Catalog》,当他们将要完成出版时,他们发出了停刊号。那是在七十年代中期,而我正是你们的年纪。停刊号的封底有一幅清晨乡间小路的照片,那种小路只有足够有探险精神的人才会走。在照片的底部有一行字:保持饥饿,保持愚蠢。 那是他们的离别赠言。保持饥饿,保持愚蠢。我总是希望自己可以那样。如今,你们将要毕业开始一段崭新的旅程,我祝愿你们也能如此。

保持饥饿,保持愚蠢。

谢谢大家。


此文是Apple创始人,CEO Steve Jobs在Stanford university毕业典礼上的演讲《you'v got to find what you love》,又译做:我生命中的三个故事。