2009年11月27日星期五
google wave邀请
2009年10月29日星期四
在linux下快速安装一个测试版的Mysql5.4
在64位机器上打算安装一个最新的Mysql5.4,下载rpm安装莫名不能使用,版本下错了?!于是转到快速搭建一个mysql,使用上没什么区别。
这里有个参考不知道是在网上到处copy的,可以作为过程参考:http://hi.baidu.com/tim_bi/blog/item/c7a3dd07cf877fca7a894769.html。
这里介绍更为简单。
1. 下载
到http://dev.mysql.com/downloads下找具体版本的mysql,选择Linux (non RPM packages)软件包:mysql-5.4.3-beta-linux-i686-glibc23.tar.gz,其它版本一样。
2. 安装
把此文件包cp|mv到你的home目录,
$tar -zvxf mysql-5.4.3-beta-linux-i686-glibc23.tar.gz
解压后产生一个目录,建议吧此目录名修改短点,如mysql5.4,这样后面好操作点。
$mv mysql-5.4.3-beta-linux-i686-glibc23 mysql5.4
$cd mysql5.4
$cd scripts
创建系统库
$./mysql_install_db --user=用户名&
3. 启动
在mysql5.4目录下
$bin/mysqld_safe --user=用户名&
有输出,回车退出。
$bin/mysql -u root
进入mysql命令行,说明数据库已经可以了。
4. 修改mysql root密码
mysql>GRANT ALL PRIVILEGES ON *.* TO root@localhost IDENTIFIED BY "新密码"
不要把localhost修改为%,保证root用户不能通过网络访问。
也可以使用:
$bin/mysqladmin -u root password 新密码
修改以后,再使用root登陆就要
$bin/mysql -u root -p
再输入密码即可。
5. 停止
$bin/mysqladmin -u root -p shutdown
2009年10月26日星期一
翻墙,良民参考,ubuntu9设置tor源
前面一篇说的是ubuntu8,我没安装9,据说没有tor源,现设置源:
deb http://mirror.noreply.org/pub/tor etch main
deb-src http://mirror.noreply.org/pub/tor etch main
sudo apt-get update
sudo apt-get install tor
其他一样,未验证,估计可以。
被墙的滋味不好受,良民参考,ubuntu
好文参考:http://ow.ly/vo5u
我的是ubuntu8.0.4,开始配置时老是不成功,怀疑tor版本过低,所以就重新安装了一下tor,覆盖原来的tor。
- 安装tor
输出一下内容:
正预备替换 tor 0.1.2.19-2 (使用 .../tor_0.2.0.34-1~hardy+1_i386.deb) ...
Stopping tor daemon: tor.
正在解压缩将用于更替的包文件 tor ...
正在设置 tor (0.2.0.34-1~hardy+1) ...
配置文件“/etc/tor/torrc”
==> 在安装后曾被修改(您或者某个脚本修改了它)。
==> 软件包的提交者同时提供了一个更新了的版本。
您现在希望如何处理呢? 您有以下几个选择:
Y 或 I :安装软件包维护者所提供的版本
N 或 O :保留您原来安装的版本
D :显示两者的区别
Z :把当前进程切换到后台,然后查看现在的具体情况
缺省的处理方法是保留您当前使用的版本。
*** torrc (Y/I/N/O/D/Z) [缺省选项=N] ? Y
替换了原来的tor以及配置文件,一定要选在Y使用新的配置文件。
- 安装privoxy
$sudo apt-get install privoxy
$sudo vi /etc/privoxy/config
最后一行一般是这个,如没有加上:
forward-socks4a / 127.0.0.1:9050 .
- 配置tor
最后几行是这样的,把UseBridge设置为1,要想获得更多的可用的bridge,可发邮件到bridges@torproject.org,邮件内容为:get bridges,很快获得几个bridge,使用这个几个新的替换下面的bridge。
#ORPort
#BridgeRelay 1
#RelayBandwidthRate 50KBytes
#ExitPolicy reject *:*
bridge 77.20.137.18:9001
bridge 69.113.18.203:9012
bridge 24.235.242.165:443
UseBridges 1
- 启动
$sudo /etc/init.d/privoxy restart
- 使用
2009年8月22日星期六
利用ln来切换python版本
安装python后(2.5和2.6)存在于/usr/bin和/usr/local/bin,在usr/bin下有个python这是指向python2.5的,系统安装时设置,在此不修改此指向。在/usr/local/bin下也有python、python2.5、python2.6,在输入python后,系统会先搜索local/bin,所以修改这里的连接就可以了。local/bin下的python其实就是2.6,可以rm -f python,若想要使用2.5:
$>sudo ln -s python2.5 python
使用2.6:
$>sudo ln -s python2.6 pyhton
以后输入pyhton就是设置后对应的pyhton版本。
还有种办法不做任何修改,就是指定版本:
$>python2.5
$>python2.6
2009年6月7日星期日
论文那些事
1 选题
论文选题非常重要,对于已经工作的同学,选择自己喜欢的 或 工作相近的,尽量不要选择对自己完全陌生的领域。这样一边作论文,一边提升自己。
全日制在校的学生,导师可能有课题做,指导得更细致一些。在职同学导师一般会引导学生做与工作相关的课题,学生是主导,导师不太干预学生写什么。
选择一个新颖的、别人没做过的基本不可能,若选择一个XXX信息系统管理、XXX人事系统管理、XXX财务管理,就没有必要了,明眼的人一看便知是数据库表的增、删、改、查,对于一个本科生作课程设计还可以。
选题不能太大,如论信息安全、分布式计算、网络等。选择更确定领域,如一种新型的分布式存储数据方式、分布式事务设计与实现、Java垃圾回收算法、SSO、商标防伪技术、XXX数据挖据算法改进等。一定要选很实在的题目,不能大而空。最好你的论文成果能使用到工作中,这样更具有说服力。
2 开题
一旦题目确定,已经明确你想作什么。这里需要回答几个问题:
- 我要做什么
- 已有那些技术或工作别人做了
- 我和他们有什么不同
- 别人工作有哪些缺点
- 我的工作有哪些优点(相比较),需要改进的有哪些
3 撰写
收集相关领域的资料,这个时间并不短,可能需要好几个月(2-3个月),在开题部分已经做了一些工作(开题时的工作成果并没有丢弃),这里需要更细致。这部分形成文字,就是相关文献、相关工作部分,一般有15页到20页,占据相当可观的篇幅。
自己做的事占据论文的绝大多数篇幅,我看过一篇论文,共60多页,文献综述部分就有近40页,这相当不好。
4 答辩
在我的blog里面已经有一篇,这可以答辩组老师写的,很有代表性。
有几点需要强调(包括的要点):
- 我做了哪些工作
- 我的创新点
- 我的挑战有那些(怎么克服)
- 优点或亮点(对比其他)
- 缺点与改进
答辩的ppt一般要求正式,不要搞得花哨,或字体翻着跟头出来。最好纯色底,加上学校的logo等,显示你对学校的自豪感。在描述流程时,需要采用一点动画,讲解到那里,就播放到哪里。
ppt的内容要合乎逻辑,不要一会是实现一会是设计(一般实现在设计之后),这样老师会迷糊,从而断定你写的论文逻辑有问题。
答辩的时间一般在15-20分钟,也就是说讲解部分只有10-15分钟,一定要把握时间,主要讲你作的工作,别过了10分钟,还在讲背景部分。ppt是用来作为你讲解的纲要,不是用来念的(念ppt会睡倒一偏),一般为标题性质为主,内容需要讲解出来。为了保证万无一失,在答辩前自己演练数次,每次记录下时间,ppt的每页需要用对应一张纸记录一下需要讲解那些内容,有了这张纸,可以更好的整理自己的思路。
最后若你有实现部分,需要有个视频,在讲解完ppt后立即播放,效果非常好。起码让老师看到你做了东西(其实只要你做了东西出来,即便有点烂,一般通过没问题),老师对你有个好的映象,老师认为你态度端正,没功劳有苦劳。
btw: 在答辩时最好穿上正装(男同胞皮鞋、领带、衬衫),头发干净整洁,表示自己非常重视这个答辩,也非常尊重答辩组老师。
个人社保:升级与数据迁移
立刻无语...
再问为什么不把老系统的数据 放到新系统中,答曰:“新系统不能用,GZ有上百万人都要重新办理。”,继续无语中...。无赖中,拿着地税局的狗屁表格,到开户行重新办理划扣,加盖银行的章,来回奔波再回到地税局办理。
一个新系统上线(或叫升级),影响到这么多的用户(据说有百万),却没有采取任何措施。在这里更多反应出该软件的设计问题,还有设计人员道德素养,与地税局本身没有太大的关系。软件升级中,数据迁移是件非常重要的事,开发方(乙方)是更本没考虑还是迫于甲方的淫威?!我想甲方也不愿意让这么多用户重新办理,除非脑袋进水。尤其对于这样的系统,平滑升级升级很重要,但却没有做到软件的可持续性(借用这个词)。明明一个程序员做到的事,却要上百万的人重复无聊的事。
程序员做的事本来就是解放人力资源,提高劳动生产力,使其能更好、更快的工作。我想这个案例,程序员的素养极其低下,又是哪个狗屁的关系项目...
2009年5月11日星期一
论文答辩准备工作(转)
导师的答辩建议。
我的一些个人体会:毕业论文答辩首先是基于之前相当长一段时间的论文工作,有了这些坚实的论文工作成果才会有好的答辩效果。但有些同学虽然有了相当好的论文工作基础,却在答辩时没有得到很好的发挥。我觉得一些常见的原因是:
1、介绍论文工作的PPT制作不精良。常见问题包括:
1.1) 未能根据自己个人喜好和论文主题选择一种好的PPT风格。其实Microsoft PowerPoint已经定义了许多可用的模板;有了这些模板后尽量不要再更改其中的风格(字体、大小、颜色、背景等),除非你对自己的审美感很有信心 (呵呵,譬如你找的GF大家都觉得很PP)。
1.2) PPT的封面没有表达足够的信息。譬如:中山大学的规范化Logo(让观众感觉到你是为自己的学校而感到自豪的)、自己的论文题目、自己的个人信息(学 号、姓名、院系、专业、email联系方式等)、指导老师信息(不是每一答辩场合都允许写明自己的导师,有些答辩会要求你在介绍中避免暴露导师的任何信 息)等。
1.3) 如果在封面上注明当天的时间(甚至地点),这会让观众觉得你是很用心地专为这次presentation而准备了PPT。
1.4) 在每一逻辑段(譬如章节),都展示同一张完整的outline(大纲),在outline中用明显颜色或字体标注下面要讲的章节,从而将一个PPT内容分 而治之地组织起来。也许有其他的方案,但无论何种技巧,你都需要将PPT的内容有机地划分,特别是内容较多时。
1.5) 在每一页PPT内容中,特忌讳有一大段的文字。PPT只适合写提纲式要点,而不适合写整段的文字。这是一些同学从论文制作PPT中很常见的缺陷,也是copy-paste这种anti-pattern的易发毛病。
1.6) 在右下角注明每页PPT的页号和总页号。页号的作用自不必说,总页号有助于观众和你自己了解你现在讲的进度如何;这也是经验不足学生易犯的毛病。
1.7) 与写论文不同,若在PPT中有引用某一参考文献,最好直接用小字体将参考文献写在本页的最下方;如果你还是像论文那样写个[n]引用参考文献,那么观众的期望自然变失望了。
1.8) 可利用写在母版上的篇眉标注作者和论文题目等信息,但不宜太突出之。
1.9) 制作一个PDF版本作为备份。因为Microsoft PowerPoint版本兼容的问题,你在家可以好好播放的PPT可能到了展示的场合却会死机;多做一个PDF格式的备份可在此时避免尴尬。
1.10) PPT应该有一个封底,通常写一些感谢答辩委员指导之类的话。
2、在演讲过程中应注意的事项:
2.1) 切忌在presentation时对着PPT中的文字来念。我知道作为一个学生,通常不喜欢这样上课的老师,因而可推断答辩委员也不会喜欢学生这种风格的宣讲。更要命的是,有些答辩委员可能会认为你根本没有准备,而从能力不足问题上升到态度不好问题。
2.2) 演讲时,大多数时间应面对答辩委员,而不要过多地低头看控制台电脑或与答辩委员同一方向看投影。呵呵,除非你觉得自己的发型太有型了,想让答辩委员多看几眼。
2.3) 在演讲前准备好笔和纸,这样在演讲后答辩委员提问时,可以做一些记录。能够让答辩委员无障碍地问完问题(不打断人家的发问也是一种礼貌),你再连续地解答这几个问题,本身也展现了你的素质和风采。
2.4) 由于答辩时间的限制,你通常没有机会演示你的实验系统或原型系统(即使你提前安装好系统也没有足够的时间演示),因而预先制作好两、三分钟的屏幕录像并为 之配音,在演讲的最后留下少许时间让答辩委员看看你的小电影是非常有益的,这有助于答辩委员相信你真的如论文中所言地完成了实验系统。
2.5) 一定要学会控制演讲的进度。有些答辩小组组长会严格按规定控制时间,这样的话如果进度控制不好就会导致自己最关键的东西还没有讲完就被停止发言了。为每页PPT编制页号和总页数有助于你控制进度。
3、当然,上面的都是形式上的东东,最关键的肯定是在presentation时说什么了:
3.1) 我建议用“提出问题 -> 分析问题 -> 解决问题 -> 评价结果”的思路展示你的论文,其中的“问题”是最重要的,这是你的challenge,也是你的contribution。用一两个精心设计的例子 (motivating examples)来解释你的“问题”是一种常见的技巧。
3.2) 对于应用背景、基础知识等introduction部分千万不要展开来说,好像你要做一个搞科普的志愿者似的。这些内容如果占的比例太大,会冲淡你自己的 工作,甚至让答辩委员觉得你好像都在介绍别人的东东,而自己却没有做什么工作。演讲的主要内容应是自己的工作,如果你真的投入了应该投入的时间和精力做论 文,应该有许多自己的工作需要花时间讲的;用一两句话讲完introduction部分本身就让人觉得你急着把别人的已有工作介绍完,是因为你需要留下大 量时间来介绍自己的工作。
3.3) 一定要强调自己有什么contribution,即自己在理论、方法、技术、工具等方面有什么贡献。
3.4) 一定要强调自己所解决的问题是有challenge的,如果是一个让人感觉太trivial的问题,其解决方案是显而易见的,那么你的工作意义就不大了。
3.5) 一定要有related work的介绍以及与你的论文工作成果的比较。如果没有这一部分,会全人一种闭门造车的感觉。
3.6) 一定要有evaluation部分。通常你需要论证你做的论文工作解决了你在论文中提出的问题,但是否真的如你所言般解决了问题呢,这需要 evaluation。一种evaluation是从理论上建模并进行推导、证明;譬如说你在论文提出的某种算法改进了原算法的时间性能,那你可以通过算 法分析从理论上证明诸如从O(n*n)改进为O(n*log.n)等。另一种evaluation是通过实验的设计和执行、数据收集与分析得出结论,例如 通过算法的实际执行时间的图表(论文中应该图、表兼有,但PPT中最好有图就够了)支持你的结论;如果你能够对Empirical Software Engineering有一些基本知识,那么实验结果会表述得更好。将两种evaluation同时做好,更有利于让读者或答辩委员觉得你的论文结论令人 信服。
3.7) 在介绍自己的方案设计时,最好展示一个完整的design space,不要让人觉得你好像只知道这一种设计方案而不知有其他可选的设计似的。注意design本身就是一个trade-off and consequence的过程!
最近太多事情,没有时间写再多了。
欢迎各位老师也根据自己的经验给同学一些建议;欢迎各位同学拍砖。
2009年5月6日星期三
javascript input 计时激活
<script language="javascript">
var activeTime = 8;
if( activeTime > 0 ) {
document.getElementById("move_check_btn").disabled=true;
var timer = setInterval('flush()', 1000);
} else {
document.getElementById("move_check_btn").disabled=false;
}
function flush(){
document.getElementById("move_check_btn").value=activeTime + '秒后重新激活';
activeTime--;
if(activeTime <= 0) {
clearInterval(timer);
document.getElementById("move_check_btn").value='点击重新激活';
document.getElementById("move_check_btn").disabled = false;
}
}
</script>
2009年4月20日星期一
2009年4月19日星期日
初始化是有顺序的
private static Abc abc = new Abc();
private static Map STORE = new HashMap();
private Abc() {
_init();
}
public static Abc createAbc() {
return abc;
}
/**
* 初始化
*/
private void _init() {
STORE.size();//报Null异常
}
}
把代码中的2句颠倒即可:
private static Abc abc = new Abc();
private static Map STORE = new HashMap();
->
private static Map STORE = new HashMap();
private static Abc abc = new Abc();
这是初始化时,先执行了new Abc(),在Abc里再执行_init,所以还没有执行STORE赋值,所以为Null。
2009年4月15日星期三
印度项目质量管理经验
原作者:佚名 由网友:转载
计算机和通信技术的迅速发展,特别是Internet技术的发展与普及,为企业内部、企业与外部提供了 快速、准确、可靠的信息交流渠道。信息化企业运作管理系统已成为企事业单位参与全球市场竞争的必备支持系统。正是由于这样的市场需求与技术发展现状,为我 国的IT行业带来了空前发展的机遇,特别是软件行业。软件企业能否抓住这样一个难得的发展机会需要多方面的努力,其中软件质量保障在其发展过程中占有重要 的位置。 众所周知,印度已成为世界上软件业增长最快的国家,目前每年软件业产值达数十亿美元,并且还在以每年30%~50%的速度增长。比较我国和印度的软件产 业,就不难发现:中国拥有巨大的软件市场和世界公认的软件开发资源,在基础研究和对技术前瞻性的把握上,也有自己的优势,就整体社会经济环境而言也优于印 度。此外,中国的软件开发人员费用比较低廉,仅是世界市场的1/3左右。虽然中国人并不缺乏软件开发的天赋,但是在越来越强调规模化经营的今天,先天不足 的管理痼疾使我们举步维艰,难以摆脱小作坊式的软件开发模式。而印度软件业从一开始就立足于为美国软件企业服务,并遵循其软件开发的管理模式,与国际标准 接轨。
管理上的问题不能得到彻底的解决,软件的质量保障就无从谈起。笔者最近在与印度一家通过了CMM4级评估的软件公司(以下 简称A公司)进行合作的过程中,较为详细地了解了他们有关项目管理的一些详细情况,更深刻地感受到了项目管理的规范化与企业软件质量保障之间的密切关系。 下面想着重从软件企业的构架,软件项目计划、项目管理、项目经理的职责等方面对印度软件的项目管理及我国软件质量保障应注意的问题进行一些经验总结,供业 内人士参考。
1.软件企业的组织结构
(1)A公司结构
图1是A公司的组织结构图,同国内公司差异较大的部门有QA、SSG和人力资源部门。
* A公司中,QA(Quality Assure)部门与研发部门独立,负责监督流程的执行。QA同时负责领导与研发部门组成的联合工作组,制定公司流程。
* SSG(System Support Group)类似我们的IT部门,负责公司所有计算机软件和硬件资源的分配和管理。所有的办公环境和开发/实验室环境由SSG负责安装和维护,计算机资源 属于SSG,由各个项目向SSG提出需求,项目结束后,设备需要交还给SSG。个人和项目组没有固定的软件和硬件资源。SSG是与研发平行的部门。
* 人力资源部门负责公司的人力资源管理,并维护员工的技能数据库。项目开始时,项目组向人力资源申请人力,向SSG申请计算机硬件和软件。项目结束时需要释 放计算机资源给SSG,释放人力资源到人力资源池,并同时更新员工的技能数据库。研发部门的人力资源由研发总负责人和其助手分配(类似我国各公司的人力资 源部)。
(2)项目组结构
1) A公司对项目组进行独立核算,项目具体负责人为PC(Project Coordinator),负责项目计划和执行,对项目具体成员进行分工。在每个阶段的结束会议上(如概要设计结束),PC要接受QC(Quality Coordinator)的审查。除了PC与QC的接口外,所有其他外部接口都由EM(Engineer Manager)完成,EM负责与客户打交道,向SSG、人力资源要求资源,与其他项目组协调进度。
2) 汇报关系为:
Team Member->Team Leader->PC->EM->研发总负责人。
3) 印度工程师分为7级,半年一次考评,即半年有一次升级机会。
1级:Software Engineer,刚毕业的本科生和研究生。
2级:Senior Software Engineer。
3级:Project Leader。
4级:Project Manager。
5级:Senior Project Manager。
3级可以成为PC,4级可以成为EM。刚开始平均2年升一级,越往后升职越慢。
A公司规定,一人最多可以同时兼任两个项目的PC,EM管理的项目没有限制。
A公司通常的项目组为4到5人,最多不超过10人。
以上是A公司(同时也是印度大多数规范化的软件公司)的组织结构和项目组结构。可以看出,A公司的组织结构非常清晰,各个部门分类非常细,任务明确,软 件生产的每一个步骤都有专门的部门、专门的人员负责,从最基础的开发人员到负责统领全局的总经理,层层管理,沟通渠道畅通。而在我国,管理的不规范往往首 先体现在公司的组织结构上,集中表现为部门的缺失和管理的交叉上。我国的软件公司,大部分规模较小,开发人员超过100人的公司很少。在印度,软件公司无 论大小,都是"麻雀虽小,五脏俱全",绝不会因为公司的规模大小而改变合理的组织结构。因此笔者认为,国内的软件企业要想有效地保障产品质量,首先就要在 构架合理的组织结构上下功夫,这就如同盖高楼首先要打好地基一样,地基不打牢,结构不合理,其他方面再下功夫也是徒劳。有人说,因为国内软件企业规模小, 所以造成结构设置的欠缺,但笔者认为恰恰是因为没有建立一个规范化的组织结构,才会使软件产品质量不保,进而严重影响了企业的发展扩大。
2.项目计划
凡事预则立,不预则废。这里的"预"就是指计划。对于软件企业,计划的重要性是不言而喻的。让我们先看看A公司的项目计划是如何制定的:在A公司,项目 开始之前必须先估计项目的规模(以代码行数来衡量);然后制定项目计划。通常时间为2~3周,已知的最长有5周。EM负责制定项目 EWP(Engineer Work Paper),其中定义了项目需要的人力和计算机资源,由相关部门同意,并报研发总负责人批准后才能开始项目。
项目的正式开始时间由项目组的Kickoff Meeting算起,Closeout Meeting结束。
大概很多人都听过这样一句话:"计划赶不上变化"。这种"变化"对某些行业而言也许并不会产生太大的影响,但对于软件企业而言,却会给软件产品的质量保 证带来严重的负面影响。为什么会造成这种"计划赶不上变化"的现象?究其原因,笔者认为主要是因为对计划的重视程度不够,计划过于笼统、粗糙导致可执行性 太差,再加上一些人为因素的影响,必然会产生这样的后果。
如果我们的软件企业都能像A公司这样,在作计划时能考虑到每一个细节, 不是仓促做出决定,而是由所有的相关部门共同对产品计划进行反复研究、制定、讨论、修改,最终形成一套系统、严密、具有很强的可执行性的计划。计划一旦形 成,就严格按照计划去执行,而不受某个人、某件事的影响,那么就不仅能够减少大量资源的浪费,产品的质量也得到了保障。
因此,对计划的高度重视、周密制定、严格执行是企业有效保障产品质量的一个重要环节。
3.项目管理
当企业构架了合理的组织结构并制定了缜密的计划后,就进入了产品的开发阶段。在这个阶段中,项目管理起了重要作用,它所涉及的环节相当具体复杂,下面先介绍一下A公司在项目管理上的具体细节:
(1)开发阶段和项目周期
开发阶段比较明显,注重各阶段应完成的功能,对本阶段应完成的工作不能留到下一阶段。
(2)流程
* A公司对流程比对项目更重视。
* 软件开发流程非常规范和系统化,其流程的可执行性很高,并且能在实践过程中不断改进。A公司的流程已覆盖到了一个项目研发的所有方面,包括从最开始的意向到最后软件的版本发布(release),都有相应的流程规定,基本上已形成一种工业化的软件开发。
* 人和流程是保证项目成功的两个最关键因素。由好的人按好的流程进行项目开发,才能最大限度地保证项目的成功。一个好的流程可以保证差的人做出来的东西不至于太差,但不能确保做出精品。通过流程可以实现一种规范化、流水线化、工业化的软件开发。
(3)计划
1) 计划详细、周到。
2) 流程中明确定义开发阶段。
3) 每个阶段都列出了该阶段的各项活动,并详细描述每项活动的属性:
* 进入条件,输入;
* 验证方法;
* 结束条件,输出。
4)每个阶段结束都要召开阶段结束会议。前一个阶段结束才能进入下一阶段。
5)计划中每个活动都比较具体,每个活动的时间以天(半天)为单位。计划包括了开展质量控制活动的时间。
(4)Review
按印度公司流程,一般把Review和测试作为保证软件质量两个主要手段。测试的重要性就不需说明了,而Review则是一个非常简单有效并能尽早发现 软件中错误的方法,可以说,任何交付物都要经Review后才能进行基线化。目前A公司有很详细全面、可执行性很高的Review流程和各种交付物的 Review Checklist。
在印度软件企业,现有这么一句口号:凡事有计划,凡事必review。
(5)QA
QC(质量经理)作为质量保证部门(SQA)的代表,监督和保证项目的进展遵循QMS各项流程和模板,并且收集项目中发现的一些问题和解决方法以优化流程。
(6)度量数据
CMM中比较强调用数据说话,对项目过程中基本上所有的数据都会有记录,最后把收集的数据提交质量保证部门进行分析,以改进流程。A公司的项目经理和质 量经理很重视项目中的数据收集,包括各种Review数据、测试数据以及项目组员每天的活动数据等。项目经理也要维护一个项目档案,在这个项目档案中可以 说包含了项目开发过程中所有的产出、开发活动、管理活动等的记录。可以这么说,有了这个项目档案,你就可以完全了解这个项目的开发过程。
(7)团队精神
印度公司都比较强调团队精神、合作精神,应该说,其流程本质上就要求员工之间的互相协调和理解。相对而言,印度员工的合作精神和协调精神都比我国员工要好得多。
(8)培训
印度公司都比较强调培训,一般有专门的培训部门进行协调。在新员工进入公司后都会有公司流程和其他一些公司普遍章程的培训,以保证员工对流程的理解和执 行。对于具体项目,项目经理在制定项目计划时就会在项目计划中提出所有的培训需求,包括技术上的培训和其他所需的培训。
(9)配置管理
在项目正式开展前,项目经理就要制定配置管理计划,并且指定配置管理员建立起配置管理库,按配置流程严格进行配置管理。在配置流程中也详细提供了对更改的控制,没有经过批准的更改请求是绝对不能进行的。
(10)记录
记录及时、充分、比较准确。这些记录包括:重要的邮件、会议纪要、审核记录、缺陷报告、测试报告。
1)与客户和其他项目组的所有往来必须邮件记录。
2)对所有的活动都有一个跟踪落实的过程,比如对所有的Review记录和更改请求都会有一个状态标识,标识其当前状态,通过跟踪其状态来监督其落实。
3)对所有的活动,包括对文档和代码的更改都会有一个历史记录。
4)记录比较准确、比较客观。
5)许多记录都是通过定量的数值记录,强调以数据说话(CMM4级的重点就是量化管理)。
以上是A公司在项目管理中所涉及到的一些主要环节,很值得国内的软件企业在制定项目管理规划时借鉴。除此之外,我国的软件企业在产品开发管理的过程中,还易出现以下几个方面的问题:
1)需求说明差─需求不清楚、不完整、太概括、或者不可测试,都会造成问题。
2)不切实际的时间表─如果在很短的时间里要求做许多事,出现错误是不可避免的。
3)测试不充分─只能根据客户意见或系统崩溃来判断系统的质量。
4)不断增加功能─在开发正在进行过程中要求增加许多新的功能。这是常见的问题。
5)交流问题─如果开发人员对客户的要求不了解,或者客户由不恰当的期望,必然会导致错误。
这些问题的出现,将会对软件质量的保证产生不良影响,针对上述问题并结合A公司在项目管理方面的经验,笔者提出一些相应的解决方法,以供参考:
1)可靠的需求─应当有一个经各方一致同意的、清楚的、完整的、详细的、整体的、可实现的、可测试的需求。为帮助确定需求,可使用模型 (prototypes)。
2)合理的时间表--为计划、设计、测试、改错、再测试、变更、以及编制文档留出足够的时间。不应使用突击的办法来完成项目。
3)适当测试─尽早开始测试;每次改错或变更后,都应重新测试。项目计划中要为测试和改错留出足够时间。
4)尽可能坚持最初的需求─一旦开发工作开始,要准备防止修改需求和新增功能,要说明这样做的后果。如果必须进行变更,必须在时间表上有相应的反映。如 果可能,在设计阶段使用快速的模型,以便使客户了解将会得到的东西。这将会使他们对他们的需求有较高的信心,减少以后的变更。
5)沟通--在适当时机进行预排和检查;充分利用团组通信工具-电子邮件、群件(groupware)、网络故障跟踪工具、变更管理工具、以及因特网的功 能。要确保文件是可用的和最新的。优选电子版文档,避免纸介质文档:进行远距离联合作业及协作;尽早使用模型,使客户的预想表达清楚。
4.PC(项目经理)
项目经理是项目成败的关键人物,其对项目的成败负主要责任。因此在这里将项目经理的有关内容单独提出,以A公司为例详细说明PC在整个产品研发过程中所扮演的角色,希望能对国内软件企业的项目经理有所启示。
(1)在A公司,按流程在一个项目正式开展之前,项目经理需要完成:
* 项目计划(Project Plan):在此描述整个项目所应完成的交付物、项目时间表、培训需求、资源需求、质量保证计划以及过程和交付物的定量质量目标等。
* 项目配置管理计划(Project Configuration Plan):在此指定配置管理员,描述项目配置项列表、配置管理库、版本管理计划等等。
*项目过程手册(Process Handbook):在此描述本项目所采取的裁剪后的生命周期模型和流程。
(2)在项目开发过程中,项目经理需非常了解项目进度,进行工作任务细化、具体计划和安排项目成员工作任务等工作。对突发事件项目经理需能及时合理地进行协调。
(3)总的说来,PC安排工作有这么几个特点:
a.PC对软件开发具有丰富的经验,了解软件开发的普遍流程,了解各个阶段所需完成的工作,这是安排好项目组成员工作的前提,在A公司对PC的整体素质要求非常高。
b.在项目正式开展前,PC准备项目计划文档,在项目计划中包含了项目进度时间表,但此时间表比较粗,只能给出各个阶段和各个子阶段的起始结束日期。对 各个阶段和各个子阶段的详细工作安排和各项工作责任人只能在项目开展工程中根据项目实际情况进行安排,一般是在每周项目组例会上进行本周详细工作安排。
c.PC对工作安排往往精确到天,有时甚至精确到小时,要做到这一点,需要:
* PC对本项目进展非常了解。了解渠道通常是每周组员的状态报告和直接与组员接触了解,这也需项目组成员能如实汇报工作。
* 对现阶段或本周所需完成的工作非常了解。知道现在该做什么,并且能把各项工作进行合理细致地划分,因为各个分解的工作比较细致,因此能相对精确地评估出这些工作完成所需的时间。
* PC对项目组员的能力比较了解,安排工作时能做到有的放矢。当安排的员工对工作不熟悉时,会指定相应的组员进行协助。
* PC对组员的工作安排都比较细致饱满。一般不会出现有些员工有事干,有些员工没事干的情况,当出现这种情况或员工提前完成工作时,PC就会进行相应的协调。
d.PC在项目组例会上的工作安排一般只限于本周或甚至是过后的二、三天,一般不会太长,对长时间工作的安排容易失去精确并且不易控制。相对而言,短时 间的工作安排就比较精确而且容易控制,并且能不断根据完成的工作进行调整。当然,这就要求PC能根据项目计划中的项目时间表进行整体进度的把握。
e.项目组例会一般一周一次(时间不能太长),但必要时(如组员工作已完成或其他事情),也可在中途召开项目会议进行工作安排,一般时间都比较短(十几分钟左右,一般不超过半小时,以免浪费时间),总之,当PC觉得需要时,就会召开项目会议。
f.当项目组出现意外事件或影响项目团结的事件时,PC能及时合理协调,解决项目组内的不和谐气氛。
g.PC善于鼓励手下,发挥员工的潜能,PC往往会赞扬很好地完成了工作的组员。
从上面可以看出,对PC的能力(包括技术和管理能力)要求是非常高的,我国的软件企业往往只重视PC的技术能力,但事实上,一个只精通技术的人往往不能 成为一个合格的领导者, 笔者认为对PC而言,首先要求他能够比他的下属看得更远一步,顺利时不盲目乐观,遇到挫折时不茫然失措,使整个团队始终保持高昂的士气。
总结
以上结合印度软件项目管理的经验总结了一些我国软件质量保障应注意的问题。曾有人提出:这样一味地学习模仿,民族软件工业没有多大希望。但笔者认为,在 这个问题上不妨采取"拿来主义"的办法,对于好的,事实证明是成功的经验,首先是"占有",然后才是"挑选"和"创新"。如果能把印度的管理经验真正领会 并付诸实践,相信对我们的民族软件工业一定会起到积极的推动作用。
2009年4月14日星期二
需求分析 - 用例之父称敏捷需要更加明智
看到一篇引起共鸣的文章:http://www.infoq.com/cn/news/2009/04/Agile-Get-Smarter。copy过来,如下:
在上周举行的Software Education SDC大会上,Ivar Jacobson——用例、UML和RUP的作者——说道,敏捷开发需要“明智”。
他提到,信息技术行业是比较容易追求时尚的,而且总想去发现银弹。他举出了下面的例子:
- 十五年前,大家全都在谈OO
- 十年前,就都变成了组件、UML、统一过程
- 五年前是RUP和CMMI
- 两年前是XP
- 今天是Scrum
这些都有好的地方——但无一是我们所需,我们需要的是更加明智的工作过。他说,“明智是敏捷的进化”。
- 敏捷意味着灵活和适应
- 敏捷提供了简单、轻量级的出发点
- 明智意味着知道什么时候超越敏捷
- 知道什么时候服从规则,什么时候打破规则
- 知道什么时候按老样子做事,什么时候做出革新
- 知道什么时候增长,什么时候退缩
按照Jacobson的话说,“明智就是敏捷++” 。他接着给出了一些明智(和不明智)实践和过程的例子,这些都是他在过往这些年里发现的。其中包括:
- 人(不明智)——把过程和工具看的比人更重要
- 人(明智) ——理解软件是人构造的,而不是过程和工具!
“有工具的蠢货依然是蠢货,但是是更危险的蠢货!” - 团队(不明智) ——把团队做职责分离(需求、分析、设计等),分成烟囱管一样的小组
- 团队(明智) ——跨功能的小型(一般是10个人,或者更少)自组织团队,拥有混合技能,可以承担工作。
“软件团队就像运动队,拥有一切所需的能力去赢得成功”
- 项目(不明智)——试着遵守瀑布流程
- 项目(明智)——先做一个“皮包骨的系统”起来,证明你已经排除了所有核心风险,然后再在需要的时候往这个皮包骨的系统上加肉。
“做远景思考,分步实施”
- 需求(不明智)——想着一开始就把所有需求都定义出来(软件开发中有一点是不变的,那就是需求总是会变)
- 需求(明智)——在轻量级的需求上做先期决策,在需要的时候再增加细节——需求是可以协商的,优先级是可以变化的。
“在设计项目时考虑到需求变化”
- 架构(不明智)——预先把所有设计都做好,没有比这更糟糕的架构了。
- 架构(明智) ——架构够用就好,架构必须来自于可以执行的代码。
“先把皮包骨的系统弄起来,一步步添肉”
- 测试(不明智)——把人分成两种,一种是开发,一种是测试。不明智的测试就是“软件世界中的清洁工”——给开发收拾残局。、
- 测试(明智) ——整个团队都为质量负责,测试也是一等公民。
“不管你做什么,在验证你确实做了想做的事情之前,这事情就没算做完”
- 文档(不明智) ——机械式的填写文档模板,只是因为一些过程规则是这样规定的。
- 文档(明智)——了解“自然规律:人们不读文档”。只在必须的时候才写文档。
“关注最根本的东西——给谈话占个位子——人们会自己找出剩余的部分”
- 过程(不明智) ——不断追逐最新时尚,要求你按照最新的规则手册把一切重写。
- 过程(明智) ——不要把孩子直接扔到浴缸里:
1. 先从现有的工作方式开始
2. 找出问题所在
3. 每次只改一个实践
“人们不读过程方面的书,所以还是只做最关键的部分,其他方面大家会自己做好的。”
明智的关键因素还是关注人,正如Jacobson所说,“这终归还是你的事”。
2009年4月13日星期一
2009年4月10日星期五
java socket
//===========SMain.java
public class SMain {
public static void main(String[] args) {
new Thread(new SListener()).start();
}
}
//===========SListener.java
import java.io.IOException;
import java.io.InterruptedIOException;
import java.net.ServerSocket;
import java.util.concurrent.ArrayBlockingQueue;
import java.util.concurrent.BlockingQueue;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.ThreadPoolExecutor;
import java.util.concurrent.TimeUnit;
public class SListener implements Runnable {
public SListener() {
}
public void run() {
BlockingQueue
50);
ExecutorService serverPool = new ThreadPoolExecutor(5, 50, 30,
TimeUnit.SECONDS, blockingQueue,
new ThreadPoolExecutor.DiscardPolicy());
ServerSocket serverSocket = null;
try {
serverSocket = new ServerSocket(7777);
serverSocket.setSoTimeout(30 * 60 * 1000);
} catch (IOException e) {
e.printStackTrace();
return;
}
while (true) {
try {
serverPool.execute(new Sprocessor(serverSocket.accept()));
} catch (InterruptedIOException iioe) {
continue;
} catch (IOException e) {
e.printStackTrace();
}
}
}
}
//===========Sprocessor.java
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.io.PrintWriter;
import java.net.Socket;
public class Sprocessor implements Runnable {
private final Socket socket;
public Sprocessor(Socket socket) {
this.socket = socket;
}
@Override
public void run() {
System.out.println("接受到请求");
PrintWriter out = null;
BufferedReader in = null;
try {
out = new PrintWriter(socket.getOutputStream(), true);
in = new BufferedReader(new InputStreamReader(socket
.getInputStream()));
String cmd;
while (true) {
cmd = in.readLine();
if (cmd.equals("quit")) {
break;
}
out.write(" " + cmd);
out.flush();
}
} catch (IOException e) {
e.printStackTrace();
} finally {
try {
if (in != null)
in.close();
} catch (Exception e) {
}
try {
if (out != null)
out.close();
} catch (Exception e) {
}
try {
if (socket != null)
socket.close();
} catch (Exception e) {
}
}
}
}
//=========python client
import socket
ss = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
ss.connect(('localhost',7777))
ss.send("aaa\n")
data = ss.recv(1024)
print data
ss.send("quit\n")
2009年4月9日星期四
2009年4月7日星期二
apt-get惹的祸
害得我重新apt-get install ubuntu-desktop,花了一个多小时,还好可以了。
2009年4月6日星期一
svn merge
在trunk的工作copy目录下
1. 把分支合并到主干
svn merge -r 100:HEAD http://服务器/repos/branches/my-branch
或
svn merge -r 100:200 http://服务器/repos/branches/my-branch
2.分支的部分修改合并到主干
svn merge -r 100:150 http://服务器/repos/branches/my-branch
但要注意在下次再合并时,是从151开始
svn merge -r 151:HEAD http://服务器/repos/branches/my-branch
或
svn merge -r 151:200 http://服务器/repos/branches/my-branch
3.只合并指定版本,一般用于错误修订。在修改了某个错误时,产生一个版本号,这里假设为190,把该版本合并到trunk
svn merge -c 190 http://服务器/repos/branches/my-branch
merge还有个功能,就是回到某个版本,merge还可以倒着来,很不常用。
svn merge -r 200:150 http://服务器/repos/branches/my-branch
其实就是使用150这个修订版本,当然可以使用svn update -r 150是一样的。
获得磁盘(分区)大小
File dir = new File("/home");
System.out.println(dir.getFreeSpace());
System.out.println(dir.getTotalSpace());
System.out.println(dir.getUsableSpace()); //更接近df的可用空间,推荐使用
但输出的大小和linux下使用df输出的结果有点不一样,相近。可以使用了,不用再df结果输出到文件,再从文件读取。
注:JDK1.6以及以上适用。
2009年4月5日星期日
java获得本机ip地址
InetAddress.getLocalHost().getHostAddress()
很不幸,是127.0.0.1,不是我们想要的局域网地址,还发现此方法只是简单的获得 /etc/hosts文件信息,不信你试试看,把文件里的127.0.0.1改为其它IP,上述的代码输出的就是改过后的内容。
InetAddress.getLocalHost().getHostName()是读取文件/etc/hostname。不是我们需要的。
有个解决办法,使用NetworkInterface,代码:
Enumeration
try {
netInterfaces = NetworkInterface.getNetworkInterfaces();
while (netInterfaces.hasMoreElements()) {
NetworkInterface ni = netInterfaces.nextElement();
System.out.println("DisplayName:" + ni.getDisplayName());
System.out.println("Name:" + ni.getName());
Enumeration
while (ips.hasMoreElements()) {
System.out.println("IP:"
+ ips.nextElement().getHostAddress());
}
}
} catch (Exception e) {
e.printStackTrace();
}
(格式太难看,copy之,格式化之,ctrl+shift+F)
这里需要注意的是输出了所有的网络接口信息,包括回环接口(lo),以及IPv6信息。下面作些过滤,只取出eth0的ipv4地址:
Enumeration
try {
netInterfaces = NetworkInterface.getNetworkInterfaces();
while (netInterfaces.hasMoreElements()) {
NetworkInterface ni = netInterfaces.nextElement();
String name = ni.getName();
if (name.equals("eth0")) {//若有多网卡清调整程序
Enumeration
while (ips.hasMoreElements()) {
InetAddress ipv4 = ips.nextElement();
if (ipv4 instanceof Inet4Address) {
System.out.println("IP:"+ ipv4.getHostAddress());
break;
}
}
break;
}
}
} catch (Exception e) {
e.printStackTrace();
}
2009年3月27日星期五
virtualbox
安装,一会就好了:
$sudo apt-get install virtualbox
运行:
$virtualbox
但是运行却报错:
VirtualBox kernel driver not installed. The vboxdrv kernel module was either not loaded or /dev/vboxdrv was not created for some reason. Re-setup the kernel module by executing '/etc/init.d/vboxdrv setup' as root.
VBox status code: -1908 (VERR_VM_DRIVER_NOT_INSTALLED).
还有-1909的错误,网上还不少人出这个错误,搜索一下一把。归结为内核模块未安装,以及权限:
$sudo apt-get install virtualbox-ose virtualbox-ose-modules-$(uname -r)
$sudo chmod ugo+rw /dev/vboxdrv
安装好了,再试试!!
2009年3月20日星期五
数据库翻页
select * from ( select rownum idx,* from TableName ) where idx >= ? and idx <= ?
2.SQL Server
select top @pagesize * from tablename where id notin (
select top @pagesize*(@page-1) id from tablenameorder by id
) order by id
3.MySQL
select * from tablename limit position, counter
4.DB2
select * from (
select *,rownumber() over(字段 ASC) as idx from TableName )
where idx >= ? and idx <= ?
公钥私钥SSL
1,公钥和私钥成对出现
2,公开的密钥叫公钥,只有自己知道的叫私钥
3,用公钥加密的数据只有对应的私钥可以解密
4,用私钥加密的数据只有对应的公钥可以解密
5,如果可以用公钥解密,则必然是对应的私钥加的密
6,如果可以用私钥解密,则必然是对应的公钥加的密
明白了?
假设一下,我找了两个数字,一个是1,一个是2。我喜欢2这个数字,就保留起来,不告诉你们,然后我告诉大家,1是我的公钥。
我有一个文件,不能让别人看,我就用1加密了。别人找到了这个文件,但是他不知道2就是解密的私钥啊,所以他解不开,只有我可以用数字2,就是我的私钥,来解密。这样我就可以保护数据了。
我的好朋友x用我的公钥1加密了字符a,加密后成了b,放在网上。别人偷到了这个文件,但是别人解不开,因为别人不知道2就是我的私钥,只有我才能解密,解密后就得到a。这样,我们就可以传送加密的数据了。
现在我们知道用公钥加密,然后用私钥来解密,就可以解决安全传输的问题了。如果我用私钥加密一段数据(当然只有我可以用私钥加密,因为只有我知道2是我的私钥),结果所有的人都看到我的内容了,因为他们都知道我的公钥是1,那么这种加密有什么用处呢?
但是我的好朋友x说有人冒充我给他发信。怎么办呢?我把我要发的信,内容是c,用我的私钥2,加密,加密后的内容是d,发给x,再告诉他解密看是不是c。他用我的公钥1解密,发现果然是c。这个时候,他会想到,能够用我的公钥解密的数据,必然是用我的私钥加的密。只有我知道我得私钥,因此他就可以确认确实是我发的东西。这样我们就能确认发送方身份了。这个过程叫做数字签名。当然具体的过程要稍微复杂一些。用私钥来加密数据,用途就是数字签名。
好,我们复习一下:
1,公钥私钥成对出现
2,私钥只有我知道
3,大家可以用我的公钥给我发加密的信了
4,大家用我的公钥解密信的内容,看看能不能解开,能解开,说明是经过我的私钥加密了,就可以确认确实是我发的了。
总结一下结论:
1,用公钥加密数据,用私钥来解密数据
2,用私钥加密数据(数字签名),用公钥来验证数字签名。
在实际的使用中,公钥不会单独出现,总是以数字证书的方式出现,这样是为了公钥的安全性和有效性。
二,SSL
我和我得好朋友x,要进行安全的通信。这种通信可以是QQ聊天,很频繁的。用我的公钥加密数据就不行了,因为:
1,我的好朋友x没有公私钥对,我怎么给他发加密的消息啊? (注:实际情况中,可以双方都有公私钥对)
2,用公私钥加密运算很费时间,很慢,影响QQ效果。
好了,好朋友x,找了一个数字3(注:会话密钥),用我的公钥1,加密后发给我,说,我们以后就用这个数字来加密信息吧。我解开后,得到了数字3。这样,只有我们两个人知道这个秘密的数字3,别的人都不知道,因为他们既不知x挑了一个什么数字,加密后的内容他们也无法解开,我们把这个秘密的数字叫做会话密钥。
然后,我们选择一种对称密钥算法,比如DES,(对称算法是说,加密过程和解密过程是对称的,用一个密钥加密,可以用同一个密钥解密。使用公私钥的算法是非对称加密算法),来加密我们之间的通信内容。别人因为不知道3是我们的会话密钥,因而无法解密。
好,复习一下:
1,SSL实现安全的通信
2,通信双方使用一方或者双方的公钥来传递和约定会话密钥 (这个过程叫做握手)
3,双方使用会话密钥,来加密双方的通信内容
上面说的是原理。大家可能觉得比较复杂了,实际使用中,比这还要复杂。不过庆幸的是,好心的先行者们在操作系统或者相关的软件中实现了这层(Layer),并且起了一个难听的名字叫做SSL,(Secure Socket Layer)。
2009年3月17日星期二
2次出现String.repalce问题
public class Test {
public static void main(String[] args) {
String ss = "aaa $VALUE$ bbb";
System.out.println(ss.replaceAll("$VALUE$", "ccc"));
}
}
说明这个$符号还真不能乱用。结果如下(没变):
================
aaa $VALUE$ bbb
2009年3月15日星期日
js对url编码
查到的信息如下==================================
javascript 常用的编码格式有:escape(), encodeURL(), encodeURIComponent() 区别如下:
escape() 方法:
encodeURI() 方法:
encodeURIComponent() 方法:
2009年3月13日星期五
mvn有时让人费解
The plugin 'org.apache.maven.plugins:maven-resources-plugin' does not exist or no valid version could be found
以前用还好好的,为什么突然报错,配置错了(这期间没有修改)。再使用-U试试,又可以了:
mvn -U compile
-U参数的含义:
-U,--update-snapshots Forces a check for updated releases and
snapshots on remote repositories
呵呵,在编译时需要联到remote服务器上,虽然我在本机上架上一个伺服器,作为maven中心库的代理。在每次编译时,即使不使用到网上的库(本地伺服器中心已经有),但还要使用网络,若网络不通,编译等操作不成功。
2009年3月8日星期日
2009年3月4日星期三
java的一小陀问题
- 1. 多线程jdk5的线程包
同步,线程安全。
- 2. jvm垃圾回收机制、jvm优化。
- 3. JVM装载,以及classload,Class.forName
- 4. ThreadLocal
- 5. 反射,动态代理
private Logger logger = Logger.getLogger(this.getClass().getName());
public void processBusiness(){
//business processing
System.out.println(“here is business logic”);
}
}
BusinessInterface businessImp = new BusinessObject();
InvocationHandler handler = new LogHandler(businessImp);
BusinessInterface proxy = (BusinessInterface) Proxy.newProxyInstance(
businessImp.getClass().getClassLoader(),
businessImp.getClass().getInterfaces(),
handler);
proxy.processBusiness();
- 6. 字节码操作CGLIB
- 7. 系统优化
- 8.
2009年2月27日星期五
获得AUTO_INCREMENT字段值
CREATE TABLE tab1 (
id INTEGER UNSIGNED NOT NULL AUTO_INCREMENT,
name VARCHAR(64) NOT NULL,
PRIMARY KEY(id)
)
一般在Statement.executeUpdate执行insert语句时,返回影响的记录条数,就是1。但我们还需要得到ID值,返回给客户程序,刚刚插入的记录的ID(代表这个记录)。一般有几种办法:
1 在执行insert语句后,再执行SELECT @@IDENTITY AS ID 或 select last_insert_id() as id都是一样的。
2 ibatis做法和上面一样
<insert id="insertTab1">
insert into tab1
(name)
values
(#name#)
<selectKey resultClass="int" keyProperty="id" >
SELECT @@IDENTITY AS ID
</selectKey>
</insert>
3 通过Statment返回auto的值
pstmt = conn.prepareStatement("insert ...",Statement.RETURN_GENERATED_KEYS);
pstmt.setString(1, "name");
pstmt.executeUpdate();
rs = pstmt.getGeneratedKeys();
rs.next();
int id = rs.getInt(1);
String StringBuffer StringBuilder
StringBuffer是可变类型,可以修改,不会频繁创建对象,并且线程安全,看看源码就知道了,有很多synchronized,在使用性能上要优于String。
StringBuilder和StringBuffer一样,只是少了synchronized,在多线程下不安全,但在使用StringBuilder时,有多少是在多线程下呢?!一般90%以上不在多线程下。推荐使用。
使用的优先顺序StringBuilder > StringBuffer > String
2009年2月25日星期三
java.net.BindException: Permission denied
却报出:java.net.BindException: Permission denied错误,在网上看到一段话,解决自己的疑问
-----------------------------
In UNIX environments port numbers below 1024 are reserved and can be bound or used only by root (superuser). So if the non-root users try to run the application they will receive an error message saying that
"java.net.BindException: Permission Denied"
There are two ways to avoid this exception. One way is to login as root and run the program. The other way is to specify a port greater than 1023
2009年2月19日星期四
String replace有问题吗?!
System.out.println("abacae".replaceAll("a", "$"));
执行结果:
@b@c@e
Exception in thread "main" java.lang.StringIndexOutOfBoundsException: String index out of range: 1
当替换成$时就出异常,没兴趣再查就String实现,自己实现得了不过就3行代码:
int idx;
while((idx = input.indexOf("a")) != -1){
input= input.substring(0, idx) + "$" +input.substring(idx + 1);
}
2009年2月15日星期日
2009年2月3日星期二
可能不知道我在说什么
1. 在action或screen(就是servlet)里
创建一个Command(代表一次请求)对象,信息包括请求的AO对象名、调用AO对象的方法名、和这次请求的参数需要封装(一般用到DO对象)到该Command对象里。
cmd = new CommandSurport("xxxAO", "xxxMethod");
cmd.setParameter();//其实就是放到Map里。
2. 还是在那个action里
在Spring容器中,选择一个CommandDispatcher,其实就是CommandDispatcherLogic(奇怪没有根据Command对象选择)。CommandDispatcher的作用就是把Command分发出去,其实就是执行的开始。
CommandDispatcher.execute(cmd);
3. 在CommandDispatcher.execute里
根据Command对象里的AO名信息从spring里获得(创建)指定AO对象(非单例)。在这里同时使用到spring的BeanPostProcessor(实现类为ApplicationObjectPostProcessor),把command设置到AO对象(其实是AO的父类ActionEvent)里。并把Command对象的参数(在第一步设置的),设置到AO对应的属性上(参看ApplicationObjectPostProcessor类)。
4. 执行AO.execute()
execute方法是在AO的父类ActionEvent里。
根据Command信息后的要调用的方法名如abc(第1步设置的),调用的AO对象的doAbc方法。
这个doAbc就是我们业务要做的。在这个AO对象里,有Command对象(在父类ActionEvent属性里)、和最主要的请求参数已经设置到AO对象的属性上了。有了这些就可以实现我们想要的逻辑。
到此完成,已经很清楚,没有必要有序列图。
逗了一个圈子,在doAbc里根据请求信息,执行业务逻辑。不知道这样做的好处是什么!?
自己常用的eclipse快捷键
ctrl + shift + f 格式化代码
ctrl + shift + t 搜索类型
ctrl + shift + r 搜索资源
ctrl + shift + o 导入
ctrl + shift + g 查看对某class的引用
alt + shift + r 改名
ctrl + / 注释和解注
F3 打开类、方法定义
F4 打开类的层次结构视图
F2 调试是显示一些值 和 类方法说明
F5 debug step into(跳进)
F6 debug step over(单步)
F7 debug step return(跳出)
F8 run 到下一个断点
ctrl + m 视图放大、缩小
ctrl + F8 切换视图
ctrl + d 删除当前行
2009年1月29日星期四
IBM ThinkPad R61i 7650CHC 无线网卡驱动安装
1. 下载驱动网址:http://snapshots.madwifi-project.org/madwifi-hal-0.10.5.6/
选择版本号最大的下载,我下载的是madwifi-hal-0.10.5.6-r3938-20090130。
2. tar zvf madwifi-hal-0.10.5.6-r3938-20090130.tar.gz
3. cd madwifi-hal-0.10.5.6-r3938-20090130
4. make
5. sudo make install
完毕需要重启系统。
在电池图标旁边就是无线标识。
已经能上网,但还有一个问题就是无线标识的灯不亮,有些人可能对此有点抓狂。
2009年1月20日星期二
2009年1月18日星期日
System里有那些属性
Properties prop = System.getProperties();
Iterator it = prop.keySet().iterator();
String key;
String value;
while(it.hasNext()) {
key = (String)it.next();
value = (String)prop.get(key);
System.out.println(key+": "+value);
}
大多数参数基本不需要我们关心,只有几个需要瞅几眼:
java.version 版本信息
sun.boot.class.path vm启动时装载的我们称之为标准的API(库、jar包)
java.ext.dirs vm启动时附加加载的jar,用户也可以丢进该目录(不推荐这么做),一般应用有自己的class load,如tomcat有全局的class load(tomcat下的lib)以及每个应用也有自己的class load(web-app下的lib)。
user.home 用户的OS主目录。
java.class.version 就是编译后的class文件包含编译器的版本信息,有时1.4编译后跑在1.5上,或相反,可能会抛出这种兼容性异常。
java.runtime.name: Java(TM) SE Runtime Environment
sun.boot.library.path: /usr/lib/jvm/java-6-sun-1.6.0.07/jre/lib/i386
java.vm.version: 10.0-b23
java.vm.vendor: Sun Microsystems Inc.
java.vendor.url: http://java.sun.com/
path.separator: :
java.vm.name: Java HotSpot(TM) Client VM
file.encoding.pkg: sun.io
sun.java.launcher: SUN_STANDARD
user.country: CN
sun.os.patch.level: unknown
java.vm.specification.name: Java Virtual Machine Specification
user.dir: /work/shamrock-ws/eclipse-ws/java-test
java.runtime.version: 1.6.0_07-b06
java.awt.graphicsenv: sun.awt.X11GraphicsEnvironment
java.endorsed.dirs: /usr/lib/jvm/java-6-sun-1.6.0.07/jre/lib/endorsed
os.arch: i386
java.io.tmpdir: /tmp
line.separator:
java.vm.specification.vendor: Sun Microsystems Inc.
os.name: Linux
sun.jnu.encoding: UTF-8
java.library.path: /usr/lib/jvm/java-6-sun-1.6.0.07/jre/lib/i386/client:/usr/lib/jvm/java-6-sun-1.6.0.07/jre/lib/i386:/usr/lib/jvm/java-6-sun-1.6.0.07/jre/../lib/i386:/usr/lib/jvm/java-6-sun-1.6.0.07/jre/lib/i386/client::/usr/lib/jvm/java-6-sun-1.6.0.07/jre/lib/i386::/usr/lib/mozilla/:/usr/lib/mozilla/:/usr/java/packages/lib/i386:/lib:/usr/lib
java.specification.name: Java Platform API Specification
java.class.version: 50.0
sun.management.compiler: HotSpot Client Compiler
os.version: 2.6.24-16-generic
user.home: /home/abc
user.timezone:
java.awt.printerjob: sun.print.PSPrinterJob
file.encoding: UTF-8
java.specification.version: 1.6
java.class.path: /work/shamrock-ws/eclipse-ws/java-test/bin
user.name: abc
java.vm.specification.version: 1.0
java.home: /usr/lib/jvm/java-6-sun-1.6.0.07/jre
sun.arch.data.model: 32
user.language: zh
java.specification.vendor: Sun Microsystems Inc.
java.vm.info: mixed mode, sharing
java.version: 1.6.0_07
java.ext.dirs: /usr/lib/jvm/java-6-sun-1.6.0.07/jre/lib/ext:/usr/java/packages/lib/ext
sun.boot.class.path: /usr/lib/jvm/java-6-sun-1.6.0.07/jre/lib/resources.jar:/usr/lib/jvm/java-6-sun-1.6.0.07/jre/lib/rt.jar:/usr/lib/jvm/java-6-sun-1.6.0.07/jre/lib/sunrsasign.jar:/usr/lib/jvm/java-6-sun-1.6.0.07/jre/lib/jsse.jar:/usr/lib/jvm/java-6-sun-1.6.0.07/jre/lib/jce.jar:/usr/lib/jvm/java-6-sun-1.6.0.07/jre/lib/charsets.jar:/usr/lib/jvm/java-6-sun-1.6.0.07/jre/classes
java.vendor: Sun Microsystems Inc.
file.separator: /
java.vendor.url.bug: http://java.sun.com/cgi-bin/bugreport.cgi
sun.io.unicode.encoding: UnicodeLittle
sun.cpu.endian: little
sun.desktop: gnome
sun.cpu.isalist:
一个10年(99年)的预测
记得当时在许某寝室,3个毛头小伙我、许某、陈某聊到互联网。
许某称10年内(开始是许某定得期限是5年,后来被我定的时间吓着)电脑在中国普及、互联网接入免费。互联网完全免费,但享受服务需要付费(这个我们共同点)。
我称15年内(就是这把许某吓得把5年改为10年)电脑都不会达到像今天(99年)电视一样的普及率。我是来自农村,电视在当时已经普及,每家都有。但深知电脑普及不仅需要时间,还需要知识,就目前而言即使在北京、广州、上海、深圳等大城市的居民都没有做到电脑的普及(每家都有),充其量占有量(率)比较高,更别说哪些中小城市乃至农村。
btw:现在在农村还有很多人没有见过电脑,我就是在上大学时才见过(献丑了!)。
还有我反对的许某的另外一点就是10年内互联网接入免费,我当时说起码需要15年才能达到免费接入。现在我想起是不是保守了点。前几个月我叔给我电话,问我宽带接入问题,着实吓我一跳。我叔在北京开通了2个网通的2M宽带,每年3600元,也就是每年每个需要1800元(150元每月)。我在杭州还好只是900元不到(每月75),是10M的宽带(不知现在能不能开通),相差比较大。
我一同学在广州电信工作,主要就是从事宽带这部分的工作(技术工作),提过宽带是电信很大一笔收入。以前在广州1M的ADSL还需要130元每月,现在多少不知道,估计少点或是把1M升为2M。呵呵,要电信放弃这部分收入,除非国家(即政府)完全接管互联网的建设,电信是国有(不代表国家)的并且是企业需要有利润。
对于自己的幼稚的单调的预测,现在想起还不乐观,15年也就是2014年,估计到时都没有达到今天日本的接入速度,记得一次在网上看到过数据,日本的宽带已经达到54M,而且费用极低。但我想这个趋势是改变不了,接入费用越来越低、速度越来越快。
陈某没有预测,绝不是墙头草,陈某表态完全同意许某的观点。
珠海的许某 和 西安的陈某不知道是否还记得10年前的只言片语?!估计有人要耍赖!
2009年1月9日星期五
oray凑合着用,动态域名解析
解压后,cd到解压后的目录,安装与你OS匹配的客户端,我的为ubuntu,所以我安装如下:
$tar zvxf phlinux-1.1-install.ubuntu.8.04.tar.gz
$cd phlinux_install
$sudo ./install.sh
在这过程中要求你选择服务器(默认即可)、用户名、密码、日志等,用户名和密码要仔细填写。若没有填写对直sudo vi /etc/phlinux.conf修改也可。
运行安装后若一切都对,oray的客户端会提示以及激活,你的机器(路由器上设置的机器)就已经可以对外服务。
以后启动也非常方便
$sudo /usr/local/phlinux/phlinux
设置路由器非常简单,路由器的地址一般都是http://192.168.1.1,输入user/pass。
在转发规则->DMZ主机填写要开放出去的内网机器(一般就是安装oray客户端的机器ip),说明所有访问该路由器的都会转发到内网该台机器上。
参考我的另外一个描述,就是不在oray申请的顶级域名也可免费解析到你的机器上:
顶级动态DNS解析
2009年1月8日星期四
junit的测试方法说明
/**
* 测试用例简介:测试目的、测试方法、测试流程
* <hr/>
* <b>预期业务场景:</b><br/>
* testCase的预期业务场景
* <hr/>
* <b>前提条件:</b></br>
* testCase的前提(需要哪些数据)
* <hr/>
* <b>测试方法/协议说明:</b><br/>
* 所测试的方法/协议的每个参数的具体说明:业务涵义、默认值、数据类型、值范围、异常情况对结果的影响
* <hr/>
* <b>调用结果:</b><br/>
* 所测试的方法/协议的执行后输出的结果及对数据库等的影响
* <hr/>
* @throws 异常
*/
2009年1月7日星期三
还记得自己使用过什么机器吗?
大学:
台式机 赛扬366, 内存32M->64M(升级),流行的游戏红警、星际、KOF97,除了KOF97不太流畅外,其它还好。
第一家公司:
台式机 CPU忘了,内存512M,从64M到512M是质的飞跃,感觉太爽了。
第二家公司:
IBM T23(P3 1G, 内存512M),最喜欢的一款,后来坏了换成R40e,感觉没长进
IBM R40e(赛扬1.8G , 1G)
第三家公司:
目前:IBM R61e(双核1.7, 1G内存,自己买的,准备再加条内存达到2G) 和 公司的台式机赛扬2.8G 1G内存,小家子气,无语。
解决svn通过https访问资源服务,方法诡异
$ svn commit -m ''
svn: 提交失败(细节如下): svn: 无法识别的URL方案(一般需要svn://,http://,file://等开头)“https://xxx/svn/trunk”
说明我的svn客户端不能通过https访问资源服务,缺少什么?再看下其它信息:
$ svn --version
svn,版本 1.5.5 (r34862) 编译于 Jan 5 2009,23:57:18 Copyright (C) 2000-2008 CollabNet. Subversion is open source software, see http://subversion.tigris.org/ This product includes software developed by CollabNet (http://www.Collab.Net/). 可使用以下的版本库访问模块: * ra_svn : 使用 svn 网络协议访问版本库的模块。 - 处理“svn”方案 * ra_local : 访问本地磁盘的版本库模块。 - 处理“file”方案
原来通过http访问是没问题的,说明这个svn缺少ssl支持。
回想前面安装svn1.5.5是没有把ssl编译进去,可能这里出了问题。
$sudo apt-get install libssl-dev
重新安装subversion1.5.5
$ ./configure --with-ssl
这里没有问题,但是后面死活安装不上(make就不通过)。
既然我没安装成,这时我想卸载以前安装的subversion,再重新安装,于是就
$sudo apt-get remove subversion
完成后,看看还存在不?奇迹发生:
$svn --version
svn,版本 1.5.5 (r34862)
编译于 Jan 7 2009,23:26:00
Copyright (C) 2000-2008 CollabNet.
Subversion is open source software, see http://subversion.tigris.org/
This product includes software developed by CollabNet (http://www.Collab.Net/).
可使用以下的版本库访问模块:
* ra_neon : Module for accessing a repository via WebDAV protocol using Neon.
- 处理“http”方案
- 处理“https”方案
* ra_svn : 使用 svn 网络协议访问版本库的模块。
- 处理“svn”方案
* ra_local : 访问本地磁盘的版本库模块。
- 处理“file”方案
* ra_serf : Module for accessing a repository via WebDAV protocol using serf.
- 处理“http”方案
- 处理“https”方案
看到和上面的版本信息不同的地方,就是已经有处理https的方案,这么说已经支持了https。试了一下以前不能checkout的https资源,现在可以了。无意中解决这个问题。在安装libssl-dev时提示要重启机器,我没重启,后来临睡前重启了一下机器,再做了remove subversion的操作,就这样了。
总之原因比较诡异,现在想想可能有:重启机器、删除以前版本(以前是1.4.6),那个呢?
还是洗洗睡去!
2009年1月5日星期一
subversion升级
1.下载expat-2.0.1.tar.gz
地址为:http://downloads.sourceforge.net/expat/expat-2.0.1.tar.gz
$ tar xvfz expat-2.0.1.tar.gz
$ cd expat-2.0.1
$ ./configure
$ make
$sudo make install
2.到此页面:
http://subversion.tigris.org/servlets/ProjectDocumentList?expandFolder=254&folderID=260
下载subversion-1.5.5.tar.gz和subversion-deps-1.5.5.tar.gz
3.放入同一个目录下,解开:
$tar zxvf 这2个包
$cd subversion-1.5.5
$./configure
看到有人使用,可以试试:
./configure --with-apxs=/usr/local/apache2/bin/apxs --with-apr=/usr/local/apr/ --with-apr-util=/usr/local/apr/ --with-swig=/usr/local/bin/swig PYTHON=usr/bin/python2.5 PERL=/usr/bin/perl5.8.8 --with-ssl
$make
$sudo make install
$svn --version
可以看到是1.5.5。
2009年1月4日星期日
svn忽略某些文件
2.但在cmd下却没这么好使,需要费点事。
在checkout的工程下创建.svnignore文件,把你想要忽略的文件名,可以使用通配符写入文件。svn propset svn:ignore -F .svnignore .以后使用svn status就不会有任何。
3. 修改全局配置
要忽略的加在后面即可,空格分割。