2010年3月2日

原创,转载请注明出处。

今天都在折腾project explorer,主要是在RCP里加入project explorer以后,不能正常显示,同时刷新的时候又清空那个view,非常奇怪。

最后按照eclipse.org的help的指导设置成功,
http://help.eclipse.org/ganymede/index.jsp?topic=/org.eclipse.platform.doc.isv/guide/cnf.htm

主要是要在自己的WorkbenchAdvisor类里面重写的initialize(IWorkbenchConfigurer configurer)的方法。

 1     public void initialize(IWorkbenchConfigurer configurer) {
 2         IDE.registerAdapters();
 3         final String ICONS_PATH = "icons/full/";
 4         final String PATH_OBJECT = ICONS_PATH + "obj16/";
 5         Bundle ideBundle = Platform.getBundle(IDEWorkbenchPlugin.IDE_WORKBENCH);
 6         declareWorkbenchImage(configurer, ideBundle,
 7                 IDE.SharedImages.IMG_OBJ_PROJECT, PATH_OBJECT + "prj_obj.gif",
 8                 true);
 9         declareWorkbenchImage(configurer, ideBundle,
10                 IDE.SharedImages.IMG_OBJ_PROJECT_CLOSED, PATH_OBJECT
11                         + "cprj_obj.gif"true);
12 
13         super.initialize(configurer);
14         configurer.setSaveAndRestore(true);    
15     }
16 
17     private void declareWorkbenchImage(IWorkbenchConfigurer configurer_p,
18             Bundle ideBundle, String symbolicName, String path, boolean shared) {
19         URL url = ideBundle.getEntry(path);
20         ImageDescriptor desc = ImageDescriptor.createFromURL(url);
21         configurer_p.declareImage(symbolicName, desc, shared);
22     }

然后是覆盖getDefaultPageInput方法如下

1 @Override
2 public IAdaptable getDefaultPageInput() {
3         return ResourcesPlugin.getWorkspace().getRoot();
4      }


这次得到的教训就是以后有什么问题首先查询eclipse.org,要不浪费太多时间了。

posted @ 2010-09-16 17:02 Li Ya Qiang 阅读(2250) | 评论 (0)编辑 收藏

第4章 准备

准备阶段最重要是关于HTML/CSS和Javascript如何协作的问题。

浏览器初始化顺序是首先脚步,然后是statements,最后是html。

如果在js里面直接引用body里面的element就会报错,最好是把执行脚本放到函数里调用


function initializePage() {
       
var x = document.getElementById('test');
       x.onclick 
= function () {alert('Hello world!')};
}
window.onload 
= initializePage;



一些常见的钩子

id:创建钩子最简单的方法,每个id在文档中只能使用一次。


var x = document.getElementById('hook');

class:可以为一系列的元素初始化相同的行为。

var lists = document.getElementsByTagName('ul');
for (var i=0; i<lists.length; i++) {
    
if (lists[i].className != 'menutree') continue;
    
//初始化行为
}


自定义属性:即不属于(X)HTML规范的属性,这是不合法的,但有时为了脚本的方便使用它。

var maxLength = this.getAttribute('maxlength');


名/值对:即写成如下的形式,然后从className中通过操作字符串获取状态。

<textarea class="maxlength=300"></textarea>


准备页面:设置事件处理程序,确定访问者状态,设置访问,产生内容,定义关系(relatedElement),修改文档结构。

<script>标签

defer属性:表示正在加载中的脚本不包含任何会改变HTML的指令(如document.write)。Explorer仅在页面已经完全加载之后才会执行拥有defer属性的脚本。

XHTML规定包含内容的script标签必须定义成CDATA,它会告诉XML/HTML解释器不要解析这些内容,而是直接送给脚本引擎。

<script type="text/javascript">
//<![CDATA[
alert('Hello World!');
//]]>
</script>


所有的脚本都被注册到HTML的全局对象中,同一个变量可以在多个脚本中使用,且为最后定义的那个。

当浏览器遇到script标签时,发送一个HTTP请求去获取脚本文件,解析其中的脚本,对HTML页面的分析和渲染暂停,直到脚本加载完成。

load事件会在页面完全加载时触发,window.onload = ; 多次设置onload会覆盖之前的设置,需要编写函数在同一个元素上设置多个事件处理程序。

等待load时会因为图片等造成延迟,这个问题很难解决,目前只有Mozilla支持的DOMContentLoaded事件,在文档加载完成后执行,不必等待图片。




posted @ 2010-08-21 22:42 Li Ya Qiang 阅读(186) | 评论 (0)编辑 收藏

第3章 浏览器

每种浏览器都包含一个代码引擎或渲染引擎,它负责解释Web页面上的代码,javascript解释器是其中的一部分。

Netscape4惨败之后,网景公司于1998年创立了Mozilla项目,开发了Gecko引擎,现在它支持着Mozilla, Firefox, Netscape, Camino等浏览器。

Explorer的代码引擎叫做Trident,1999年3月发布的Explorer5.0是第一个支持W3C DOM和XMLHttpRequest的浏览器,但也是最后一个包含了主要Javascript更新的Explorer版本。

Safari于2003年发布,它使用KHTML代码引擎,它是Macintosh平台的默认浏览器。

Opera是一个独立的浏览器,在浏览器大战期间,它没有实现DHTML,现在看来,这是一个相当英明的决定。

4种兼容性问题

不支持:这些出现问题的功能不是“不可或缺”的基础功能,都能够通过对象检测判断,而且浏览器也在努力消除这些问题,如document.sytleSheets来读写整个样式表,目前Safari和Opera也增加了对其的支持。

合理的不同看法:如defer属性对加载脚本的要求,Exploer有独特的理解,幸好这种问题是最少有的。

有意为之的兼容性问题:通常是浏览器大战的遗留问题,也可以通过对象检测来判断,一旦微软着手实现W3C事件标准,最后一批被故意造成的兼容性问题也将得到解决。

浏览器bug:这是由于编程的缺陷造成的不可预见的错误,它是无法解决也是无法衡量的。如Exploer6会被normalize()方法导致崩溃。

浏览器兼容性问题是单纯的生活的事实,它不会轻易消失,应该尽快地习惯它,至少听任它。

在任何情况下都不要先为某一个浏览器写脚本,然后增加其他浏览器的支持。在项目支出就应该解决这些兼容性问题,而不是放在最后。

对象检测

对象检测是避免兼容性问题的最佳助手。它的一般方法是检查想使用的对象,看它们是否存在,如果不存在,就结束函数。(if(!对象)),从技术上说,对象检测是把一个对象转换成一个布尔值。

检查W3C DOM:


var W3CDOM = document.createElement && document.getElementsByTagName;


对W3C DOM的检测使我们可以总是假设浏览器也支持相关的功能,如appendChild,而省去对它的检查。

事件处理测试:


function addEventSimple(obj, evt, fn) {
    
if (obj.addEventListener) //W3C
        obj.addEventListener(evt, fn, false);
    
else if (obj.attachEvent) //微软
      obj.attachEvent('on' + evt, fn);
}

我们期望未来的版本使用标准,所以对标准的支持应该最先检查,事实上先检查attachEvent,Fx等浏览器会报错。

浏览器检测

为什么浏览器检测行不通?浏览器兼容性模式是不断变化的,今天不支持的属性,明天可能会支持;而且浏览器常常会伪装自己的身份,以便通过浏览器检测。

浏览器检测的军备竞赛

navigator.userAgent中保存了每一个浏览器的识别字符串。1995年前后的Mosaic和Netscape年代中,由于 Netscape的cookie和<center>标签等的支持,服务器端的程序员决定使用浏览器检测来区分两种浏览器,他们检测识别字符串 是否从Mozilla/开始,这给javascript世界带来了不必要的磨难。浏览器厂商被迫将自己的识别字符串变成从Mozilla/开始,即便是 Explorer最初进入市场时也将自己伪装成了Netscape。浏览器大战开始后,Web开发者们做出反应,他们创建了更多的浏览器程序来区分 Netscape和Exploer,而当战争结束时,已经有数不清的网站设置了检测脚本只允许Explorer访问,历史重演了,一些浏览器如 Opera,又不得不修改自己的识别字符串来匹配Explorer,甚至将识别字符串的设置开放给用户。

拆解浏览器字符串

Mozilla/5.0 (Windows; U; Windows NT 5.1; en-US; rv:1.7.12) Gecko/20050915
Mozilla
/4.0 (compatible; MSIE 6.0; Windows NT 5.1; SV1; .NET CLR 1.1.4322)
Mozilla
/5.0 (Macintosh; U; PPC Mac OS X; en) AppleWebKit/312.8 (KHTML, like Gecko) Safari/312.6
Mozilla
/4.0 (compatible; MSIE 6.0; Windows NT 5.2)

第一个是Mozilla1.7.12,第二个是NT5.1(即XP)的Explorer6.0,第三个是Safari1.3.2,第四个是伪装后的Safari1.3.2。

userAgent:使用navigator.userAgent,而不是navigator.appName和navigator.appVersion。前者尚有一些遵循,后者都是谎言;

Mozilla/:只能证明浏览器是1994年后发布的;

/[version number]:没有意义,每一个现代浏览器都生命是第4版或第5版的Mozilla;

不规则字符串:通常被圆括号包围,包含这非常复杂的缩写;

Opera:唯一支持window.opera属性,可以检测这个对象来判断;

Safari, iCab和Konqueror:不像Opera那样勇于承担风险,它们可以完全地伪装自己;

Gecko:Mozilla识别串通常都会包含Gecko,但不幸Safari等也包含;

MSIE:没有意义,绝大多数的浏览器都包含MSIE;

版本号:Exploer和Opera允许在名字后面找到自己的版本号,而其他浏览器都无效,比如Mozilla的隐藏版本;

操作系统:Windows操作系统都以Win开始,当然这不适用于伪装的串。

(http://www.quirksmode.org/js/detect.html)

浏览器检测的正确使用

当你需要知道访问者的浏览器,如站点统计时,这些检测不会影响脚本逻辑。

当我们用对象检测时需要排除浏览器bug等时,可以将对象检测和浏览器检测一起使用。

调试

Mozilla有最好的错误信息,因此多在Mozilla中调试;

使用return,alert,confirm是不错的方法,复杂的调试可以自己创建一个错误控制台;

将bug报告给浏览器厂商。

posted @ 2010-08-21 22:27 Li Ya Qiang 阅读(160) | 评论 (0)编辑 收藏

第二章 大背景

javascript嵌入在一个还同时使用着HTML和CSS的环境中。

 

2002年,Stuart Langridge提出无侵入脚本编程(unobtrusive scripting)。它代表了向基于CSS的、兼容标准的Web站点的新理论中嵌入Javascript的首次认真的尝试。

它应该是可用的。即给网站带来明确的可用性好处。

它应该是可访问的。如果javascript失效,网页应该依然是可阅读和可理解的。

它应该是容易实现的。Web开发者只需要在页面中引入脚本本身和一个Javascript钩子,脚本就能运行。

它应该是分离的。只存在于自己的.js文件中,而不是散落在HTML中。

 

一个Web页面由如下三个层组成:HTML结构层、CSS表现层、Javascript行为层。

 

表现与结构的分离

所有的表现定义在一个单独的CSS文件中,HTML中不再出现<font>标签和用于表现的表格。一般通过脚本改变className来引用不同的

CSS元素。CSS (display: none)用来表示文档中的某个元素隐藏,也可以通过脚本从文档中删除这个元素。至于采用哪种方式,PPK推荐采用后一种方式。特别是对于form表单的时候,采用第一种方式就会提交很多无用的信息。

 

行为与结构的分离

所有的javascript函数都被放在一个独立.js文件中,然后把它链入所需要它的HTML页面中,HTML移除所有的事件处理程序。

钩子(hook)用来生命“在这里准备部署行为”的ID,它是注册事件处理程序的一种方法。

javascript:伪协议是复杂而肮脏的(<a href="javascript:dosomeaction()">),应该放到脚步文件中。

 

行为和表现的分离

行为和表现的分离是复杂的,尚没有任何的标准。

当若干元素部署相同的效果时,CSS是有效的,而需要创建相似但不完全相同的效果时,javascript是最有效的方法。

 

可访问性规则

条理分明的HTML,如硬编码的链接必须有href。

产生对脚本用户有意义的内容,如:

一条发送ajax请求的链接可以完全用javascript生成,这样无脚本用户就不会看到href为#的a标签而产生不解;

用javascript来隐藏一段内容,而不是用css,否则无脚本用户将永远看不到那是什么;

判断是否脚本可用,然后跳转到一个无脚本页面时,要用location.replace而不是location.href,这样在后退时不会再返回到有脚本页面,事实上location.href产生了一条历史记录;

针对键盘用户,我们对触发事件的元素增加focus动作;

由于各浏览器都支持(但不完全支持)javascript,因此<noscript>标签就显得没有意义,最好完全不用。

 

posted @ 2010-08-21 22:21 Li Ya Qiang 阅读(180) | 评论 (0)编辑 收藏

第一章:目标

javascript的目标是给Web页面增加一个额外的可用性层。

 

js分为6个部分:javascript核心、BOM(浏览器对象模型)、事件、DOM(文档对象模型)、CSS修改、数据检索(XMLHttpRequest)。

他们的任务:核心使得js成为一门编程语言的基础,控制结构变量函数和对 象;BOM给浏览器窗口下达指令,读取cookie,与其他窗口进行通信;事件找出用户执行的动作,并定义这些动作将触发的函数;DOM学习和改变 HTML文档的结构;CSS学习和改变HTML文档的CSS表现;数据检索从服务器下载新的数据而不刷新页面。

所有的脚本都是用核心语言、事件和DOM:等待行动,并更新页面。

 

ECMA(欧洲计算机制造联合协会)对javascript核心进行标准化(ECMA1.5),这个标准应用到flash、浏览器、服务器以及其他尚未产生的应用上。

W3C(万维网协会)创建了DOM规范,它也包括事件处理和CSS修改的内容。微软仍然没有实现W3C的事件规范,却使用它自己专有的事件模型。

WHAT-WG(Web超文本应用技术工作组)正为BOM标准而工作。

数据检索使用的则是微软的事实标准,W3C为数据检索推出了XMLHttpRequest规范的第一部草案。

 

<script标签中允许在language="javascript1.2"中指定版本号,但自1.2版本开始Netscape和Explorer 4都宣称支持,因此设置版本号没有意义,事实上根本不需要这个属性。

 

js遵循严格的安全规范

不允许访问宿主计算机:不能读写除cookie外的文件系统

同源策略:两个窗口的页面的Web域名必须相同,才允许跨窗口通信。同子域下可以通过设置相同的document.domain(必须设置为真实域名的一部分)进行通信。

其他限制:不能读取历史对象的属性(当可以在历史中后退);不能设置文件上传表单域的值;试图关闭窗口时会询问用户;不允许打开一个小于100x100或处于屏幕之外或没有标题栏的新窗口。

 

javascript的历史

创始人Brendan Eich当时在Netscape工作,js公开的历史从1996.3的Netscape2发布开始。

Eich最初的目标是为Web开发者提供一种简单的方式为页面增加一些交互,这些 脚本从其他页面复制过来并稍作调整就可以使用。最初命名为LiveScript。但Netscape出于市场的考虑选取了一个与当时流行的Java相似的 一个名字,并仓促地要求Eich“使这个语言看起来想Java”,从而误导人们将js视为轻量级的Java版本,看成一个可以拿来搬弄技巧而不值得引起严 谨的程序员注意的轻巧的脚本语言。

 

第一瘦时期

早期的日子里,浏览器是一个瘦客户端,表单验证和鼠标滑过的效果是令人惊艳的,但它们不允许在客户端大量进行交互,用户被迫与服务端交互。

1996~1999间Netscape与微软的浏览器大战开始,双方都推出自己的 第4版,为争夺CSS规范各不相让。两个浏览器厂商都让javascript可以控制这些CSS声明,于是就可以使用position:absolute 创建一个“层”,然后通过持续地改变top和left似的它在屏幕上移动,这才叫酷!这些小伎俩被冠以DHTML为人所知,即通过javascript来 改变css属性。

为此双方都推出了自己专有的DOM(又称过渡DOM,介于Netscap3DOM和W3CDOM之间),Netscape4支持document.layers,而Explorer支持document.all。

 

第一个胖阶段

有了这些新特性,客户端增加大量的互动:动画、隐藏和其他视觉效果,javascript的目标转向技术,而不是可用性,js进入胖阶段。

微软在1999年发布Explorer5,相当好地支持了CSS和新的W3CDOM标准。尽管公司和Web开发者尽力挽救,Netscape4还是灭亡了,差不多同一时间,js的第一个胖阶段结束,人们发现的不过是少量的javascript和大量的空话。

CSS变革开始。

 

第二个瘦阶段

浏览器大战接近尾声的时候,Web开发者们厌倦了大量的编程和变通做法,极度地想从头开始。CSS,而不是javascript,给了他们最好的机会来完全突破过去的束缚。

大概从2003年开始,一部分先锋开始用一种深受CSS革命理念影响的新方式写javascript,javascript第一次深深地潜入到全面的Web开发理论中去,而可访问性问题终于被认识到并着手解决。

无侵入脚本编程提出,但并没有立即征服世界。

 

第二个胖阶段

从服务器端悄悄地载入小块的数据,唤醒了沉睡多年的技术构思和可用性观 念,Jesse James Garrett的文章《Ajax:Web应用程序的新方法》开创了Ajax时代,javascript的用途又一次被重新定义,传统web开发者创建的是 瘦的可访问的乱糟糟的js代码,而来自服务端开发的“资深程序员们”创建的是面向对象的,胖的,可访问性差的ajax客户端。焦点又被集中在技术方面,可 用性及为什么要用ajax仍很少被关注,臃肿的库(即框架)与日俱增。

所幸人们都开始同意并遵循已经存在的标准。

 

2006.5数据显示,目前共有至少134中Ajax框架,我个人认为这股热潮已经到达了顶峰,有谁需要134种程序去做本质上是一样的事呢?

javascript将调整回瘦阶段,那时它的用途也将再次被重新定义,当然某个时期第三个瘦阶段结束后会迎来第三个胖阶段.. 从根本上,这种情况只有当每个人都只认同唯一的javascript用途时才会被打破。

posted @ 2010-08-21 22:14 Li Ya Qiang 阅读(197) | 评论 (0)编辑 收藏

1 echo 和 @
回显命令
@                     #关闭单行回显
echo off              #从下一行开始关闭回显
@echo off             #从本行开始关闭回显。一般批处理第一行都是这个
echo on               #从下一行开始打开回显
echo                  #显示当前是 echo off 状态还是 echo on 状态
echo.                 #输出一个”回车换行”,空白行
                         #(同echo, echo; echo+ echo[ echo] echo/ echo)


2 errorlevel
echo %errorlevel%
每个命令运行结束,可以用这个命令行格式 查看返回码
默认值为0,一般命令执行出错会设 errorlevel 为1


3 dir
显示文 件夹内容
dir                  #显示当前目录中的文件和子目录
dir /a               #显示当前目录中的文件和子目录,包括隐藏文件和系统文件
dir c: /a:d          #显示 C 盘当前目录中的目录
dir c: /a:-d         #显示 C 盘根目录中的文件
dir c: /b/p         #/b只显示文件名,/p分页显示
dir *.exe /s         #显示当前目录和子目录里所有的.exe文件


4 cd
切换目录
cd                  #进入根目录
cd                   #显示当前目录
cd /d d:sdk         #可以同时更改盘符和目录


5 md
创建目录
md d:abc          #如果 d:a 不存在,将会自动创建中级目录
#如果命令扩展名被停用,则需要键入 mkdir abc。

6 rd
删除目录
rd abc               #删除当前目录里的 abc 子目录,要求为空目录
rd /s/q d:temp      #删除 d:temp 文件夹及其子文件夹和文件,/q安静模式


7 del
删除文 件
del d:test.txt      #删除指定文件,不能是隐藏、系统、只读文件
del /q/a/f d:temp*.*
删除 d:temp 文件夹里面的所有文件,包括隐藏、只读、系统文件,不包括子目录
del /q/a/f/s d:temp*.*
删除 d:temp 及子文件夹里面的所有文件,包括隐藏、只读、系统文件,不包括子目录


8 ren
重命名命令
ren d:temp tmp      #支持对文件夹的重命名

9 cls
清屏

10 type
显 示文件内容
type c:boot.ini     #显示指定文件的内容,程序文件一般会显示乱码
type *.txt           #显示当前目录里所有.txt文件的内容


11 copy
拷 贝文件
copy c:test.txt d:test.bak
复制 c:test.txt 文件到 d: ,并重命名为 test.bak
copy con test.txt
从屏幕上等待输入,按 Ctrl+Z 结束输入,输入内容存为test.txt文件
con代表屏幕,prn代表打印机,nul代表空设备
copy 1.txt + 2.txt 3.txt
合并 1.txt 和 2.txt 的内容,保存为 3.txt 文件
如果不指定 3.txt ,则保存到 1.txt
copy test.txt +
复制文件到自己,实际上是修改了文件日期


12 title
设 置cmd窗口的标题
title 新标题         #可以看到cmd窗口的标题栏变了


13 ver
显示系统版本

14 label 和 vol
设 置卷标
vol                  #显示卷标
label                #显示卷标,同时提示输入新卷标
label c:system       #设置C盘的卷标为 system

15 pause
暂停命令

16 rem 和 ::
注 释命令
注释行不执行操作

17 date 和 time
日 期和时间
date           #显示当前日期,并提示输入新日期,按"回车"略过输入
date/t         #只显示当前日期,不提示输入新日期
time           #显示当前时间,并提示输入新时间,按"回车"略过输入
time/t         #只显示当前时间,不提示输入新时间


18 goto 和 :
跳 转命令
:label         #行首为:表示该行是标签行,标签行不执行操作
goto label     #跳转到指定的标签那一行


19 find (外部命令)
查 找命令
find "abc" c:test.txt
在 c:test.txt 文件里查找含 abc 字符串的行
如果找不到,将设 errorlevel 返回码为1
find /i “abc” c:test.txt
查找含 abc 的行,忽略大小写
find /c "abc" c:test.txt
显示含 abc 的行的行数


20 more (外部命令)
逐 屏显示
more c:test.txt     #逐屏显示 c:test.txt 的文件内容


21 tree
显 示目录结构
tree d:             #显示D盘的文件目录结构


22 &
顺序执行多条命令,而不管命令是否执行成功

23 &&
顺 序执行多条命令,当碰到执行出错的命令后将不执行后面的命令
find "ok" c:test.txt && echo 成功
如果找到了"ok"字样,就显示"成功",找不到就不显示


24 ||
顺 序执行多条命令,当碰到执行正确的命令后将不执行后面的命令
find "ok" c:test.txt || echo 不成功
如果找不到"ok"字样,就显示"不成功",找到了就不显示

25 |
管 道命令
dir *.* /s/a | find /c ".exe"
管道命令表示先执行 dir 命令,对其输出的结果执行后面的 find 命令
该命令行结果:输出当前文件夹及所有子文件夹里的.exe文件的个数
type c:test.txt|more
这个和 more c:test.txt 的效果是一样的


26 > 和 >>
输 出重定向命令
> 清除文件中原有的内容后再写入
>> 追加内容到文件末尾,而不会清除原有的内容
主要将本来显示在屏幕上的内容输出到指定文件中
指定文件如果不存在,则自动生成该文件
type c:test.txt >prn
屏幕上不显示文件内容,转向输出到打印机
echo hello world>con
在 屏幕上显示hello world,实际上所有输出都是默认 >con 的
copy c:test.txt f: >nul
拷 贝文件,并且不显示"文件复制成功"的提示信息,但如果f盘不存在,还是会显示出错信息
copy c:test.txt f: >nul 2>nul
不显示”文件复制成功”的提示信息,并且f盘不存在的话,也不显示错误提示信息
echo ^^W ^> ^W>c:test.txt
生成的文件内容为 ^W > W
^ 和 > 是控制命令,要把它们输出到文件,必须在前面加个 ^ 符号

27 <
从 文件中获得输入信息,而不是从屏幕上
一般用于 date time label 等需要等待输入的命令
@echo off
echo 2005-05-01>temp.txt
date <temp.txt
del temp.txt
这 样就可以不等待输入直接修改当前日期

28 %0 %1 %2 %3 %4 %5 %6 %7 %8 %9 %*
命 令行传递给批处理的参数
%0 批处理文件本身
%1 第一个参数
%9 第九个参数
%* 从第一个参数开始的所有参数

批参数(%n)的替代已被增强。您可以使用以下语法:

     %~1          - 删除引号("),扩充 %1
     %~f1         - 将 %1 扩充到一个完全合格的路径名
     %~d1         - 仅将 %1 扩充到一个驱动器号
     %~p1         - 仅将 %1 扩充到一个路径
     %~n1         - 仅将 %1 扩充到一个文件名
     %~x1         - 仅将 %1 扩充到一个文件扩展名
     %~s1         - 扩充的路径指含有短名
     %~a1         - 将 %1 扩充到文件属性
     %~t1         - 将 %1 扩充到文件的日期/时间
     %~z1         - 将 %1 扩充到文件的大小
     %~$PATH : 1 - 查找列在 PATH 环境变量的目录,并将 %1
                   扩充到找到的第一个完全合格的名称。如果环境
                   变量名未被定义,或者没有找到文件,此组合键会
                   扩充到空字符串

可以组合修定符来取得多重结果:

    %~dp1        - 只将 %1 扩展到驱动器号和路径
    %~nx1        - 只将 %1 扩展到文件名和扩展名
    %~dp$PATH:1 - 在列在 PATH 环境变量中的目录里查找 %1,
                   并扩展到找到的第一个文件的驱动器号和路径。
    %~ftza1      - 将 %1 扩展到类似 DIR 的输出行。
可以参照 call/? 或 for/? 看出每个参数的含意
echo load "%%1" "%%2">c:test.txt
生成的文 件内容为 load "%1" "%2"
批处理文件里,用这个格式把命令行参数输出到文件

29 if
判 断命令
if "%1"=="/a" echo 第一个参数是/a
if /i "%1" equ "/a" echo 第一个参数是/a
/i 表示不区分大小写,equ 和 == 是一样的,其它运算符参见 if/?
if exist c:test.bat echo 存在c:test.bat文件
if not exist c:windows (
     echo 不存在c:windows文件夹
     )
if exist c:test.bat (
     echo 存在c:test.bat
     ) else (
     echo 不存在c:test.bat
     )

30 setlocal 和 endlocal
设置”命令扩展名”和”延缓环境变量扩充”
SETLOCAL ENABLEEXTENSIONS             #启用"命令扩展名"
SETLOCAL DISABLEEXTENSIONS            #停用"命令扩展名"
SETLOCAL ENABLEDELAYEDEXPANSION       #启用"延缓环境变量扩充"
SETLOCAL DISABLEDELAYEDEXPANSION      #停用"延缓环境变量扩充"
ENDLOCAL                              #恢复到使用SETLOCAL语句以前的状态
“命令扩展名”默认为启用
“延 缓环境变量扩充”默认为停用
批处理结束系统会自动恢复默认值
可以修改注册表以禁用"命令扩展名",详见 cmd /? 。所以用到"命令扩展名"的程
序,建议在开头和结尾加上 SETLOCAL ENABLEEXTENSIONS 和 ENDLOCAL 语句,以确
保程序能在其它系统上正确运行
"延缓环境变量扩充"主要用于 if 和 for 的符合语句,在 set 的说明里有其实用例程

31 set
设置变量
引用变量可在变量 名前后加 % ,即 %变量名%
set                     #显示目前所有可用的变量,包括系统变量和自定义的变量
echo %SystemDrive%      #显示系统盘盘符。系统变量可以直接引用
set p                   #显示所有以p开头的变量,要是一个也没有就设errorlevel=1
set p=aa1bb1aa2bb2      #设置变量p,并赋值为 = 后面的字符串,即aa1bb1aa2bb2
echo %p%                #显示变量p代表的字符串,即aa1bb1aa2bb2
echo %p:~6%             #显示变量p中第6个字符以后的所有字符,即aa2bb2
echo %p:~6,3%           #显示第6个字符以后的3个字符,即aa2
echo %p:~0,3%           #显示前3个字符,即aa1
echo %p:~-2%            #显示最后面的2个字符,即b2
echo %p:~0,-2%          #显示除了最后2个字符以外的其它字符,即aa1bb1aa2b
echo %p:aa=c%           #用c替换变量p中所有的aa,即显示c1bb1c2bb2
echo %p:aa=%            #将变量p中的所有aa字符串置换为空,即显示1bb12bb2
echo %p:*bb=c%          #第一个bb及其之前的所有字符被替换为c,即显示c1aa2bb2
set p=%p:*bb=c%         #设置变量p,赋值为 %p:*bb=c% ,即c1aa2bb2
set /a p=39             #设置p为数值型变量,值为39
set /a p=39/10          #支持运算符,有小数时用去尾法,39/10=3.9,去尾得3,p=3
set /a p=p/10           #用 /a 参数时,在 = 后面的变量可以不加%直接引用
set /a p=”1&0″          #”与”运算,要加引号。其它支持的运算符参见set/?
set p=                  #取消p变量
set /p p=请输入
屏幕上显示”请输入”,并会将输入的字符串赋值给变量p
注意这条可以用来取代 choice 命令
注意变量在 if 和 for 的复合语句里是一次性全部替换的,如
@echo off
set p=aaa
if %p%==aaa (
     echo %p%
     set p=bbb
     echo %p%
     )
结果将显示
aaa
aaa
因 为在读取 if 语句时已经将所有 %p% 替换为aaa
这里的"替换",在 /? 帮助里就是指"扩充"、"环境变量扩充"
可以启用” 延缓环境变量扩充”,用 ! 来引用变量,即 !变量名!
@echo off
SETLOCAL ENABLEDELAYEDEXPANSION
set p=aaa
if %p%==aaa (
     echo %p%
     set p=bbb
     echo !p!
     )
ENDLOCAL
结果将显示
aaa
bbb
还 有几个动态变量,运行 set 看不到
%CD%                   #代表当前目录的字符串
%DATE%                 #当前日期
%TIME%                 #当前时间
%RANDOM%               #随机整数,介于0~32767
%ERRORLEVEL%           #当前 ERRORLEVEL 值
%CMDEXTVERSION%        #当前命令处理器扩展名版本号
%CMDCMDLINE%           #调用命令处理器的原始命令行
可以用 echo命令查看每个变量值,如 echo %time%
注意 %time% 精确到毫秒,在批处理需要延时处理时可以用到

32 start
批 处理中调用外部程序的命令,否则等外部程序完成后才继续执行剩下的指令

33 call
批处理中调用另外一个批处理的命令,否则剩下的批处理指令将不会被执 行
有时有的应用程序用start调用出错的,也可以call调用

34 choice (外部命令)
选 择命令
让用户输入一个字符,从而选择运行不同的命令,返回码errorlevel为1234……
win98 里是choice.com
win2000pro里没有,可以从win98里拷过来
win2003里是choice.exe
choice /N /C y /T 5 /D y>nul
延时5秒


35 assoc 和 ftype
文件关 联
assoc 设置'文件扩展名'关联,关联到'文件类型'
ftype 设置'文件类型'关联,关联到'执行程序和参数'
当 你双击一个.txt文件时,windows并不是根据.txt直接判断用 notepad.exe 打开
而是先判断.txt属于 txtfile '文件类型'
再调用 txtfile 关联的命令行 txtfile=%SystemRoot%system32NOTEPAD.EXE %1
可 以在"文件夹选项"→"文件类型"里修改这2种关联
assoc            #显示所有'文件扩展名'关联
assoc .txt       #显示.txt代表的'文件类型',结果显示 .txt=txtfile
assoc .doc       #显示.doc代表的'文件类型',结果显示 .doc=Word.Document.8
assoc .exe       #显示.exe代表的'文件类型',结果显示 .exe=exefile
ftype            #显示所有'文件类型'关联
ftype exefile    #显示exefile类型关联的命令行,结果显示 exefile="%1" %*
assoc .txt=Word.Document.8
设置.txt为word类型的文档,可以看到.txt文件的图标都变了
assoc .txt=txtfile
恢复.txt的正确关联
ftype exefile="%1" %*
恢复 exefile 的正确关联
如 果该关联已经被破坏,可以运行 command.com ,再输入这条命令

36 pushd 和 popd
切 换当前目录
@echo off
c: & cd & md mp3        #在 C: 建立 mp3 文件夹
md d:mp4                #在 D: 建立 mp4 文件夹
cd /d d:mp4             #更改当前目录为 d:mp4
pushd c:mp3             #保存当前目录,并切换当前目录为 c:mp3
popd                     #恢复当前目录为刚才保存的 d:mp4

37 for
循 环命令
这个比较复杂,请对照 for/? 来看
for %%i in (c: d: e: f:) do echo %%i
依次调用小括号里的每个字符串,执行 do 后面的命令
注意%%i,在批处理中 for 语句调用参数用2个%
默 认的字符串分隔符是"空格键","Tab键","回车键"
for %%i in (*.txt) do find "abc" %%i
对 当前目录里所有的txt文件执行 find 命令
for /r . %%i in (*.txt) do find "abc" %%i
在 当前目录和子目录里所有的.txt文件中搜索包含 abc 字符串的行
for /r . %%i in (.) do echo %%~pni
显 示当前目录名和所有子目录名,包括路径,不包括盘符
for /r d:mp3 %%i in (*.mp3) do echo %%i>>d:mp3.txt
把 d:mp3 及其子目录里的mp3文件的文件名都存到 d:mp3.txt 里去
for /l %%i in (2,1,8) do echo %%i
生成2345678的一串数字,2是数字序列的开头,8是结尾,1表示每次加1
for /f %%i in ('set') do echo %%i
对 set 命令的输出结果循环调用,每行一个
for /f "eol=P" %%i in ('set') do echo %%i
取 set 命令的输出结果,忽略以 P 开头的那几行
for /f %%i in (d:mp3.txt) do echo %%i
显示 d:mp3.txt 里的每个文件名,每行一个,不支持带空格的名称
for /f "delims=" %%i in (d:mp3.txt) do echo %%i
显示 d:mp3.txt 里的每个文件名,每行一个,支持带空格的名称
for /f "skip=5 tokens=4" %%a in ('dir') do echo %%a
对 dir 命令的结果,跳过前面5行,余下的每行取第4列
每列之间的分隔符为默认的"空格"
可以注意到 dir 命令输出的前5行是没有文件名的
for /f "tokens=1,2,3 delims=- " %%a in ('date /t') do (
     echo %%a
     echo %%b
     echo %%c
     )
对 date /t 的输出结果,每行取1、2、3列
第一列对应指定的 %%a ,后面的 %%b 和 %%c 是派生出来的,对应其它列
分 隔符指定为 - 和"空格",注意 delims=- 后面有个"空格"
其中 tokens=1,2,3 若用 tokens=1-3 替换,效果是一样的
for /f "tokens=2* delims=- " %%a in ('date /t') do echo %%b
取 第2列给 %%a ,其后的列都给 %%b


38 subst (外部命令)
映射磁盘。
subst z: serverd      #这样输入z:就可以访问serverd了
subst z: /d              #取消该映射
subst                    #显示目前所有的映时

39   xcopy (外部命令)
文 件拷贝
xcopy d:mp3 e:mp3 /s/e/i/y
复制 d:mp3 文件夹、所有子文件夹和文件到 e: ,覆盖已有文件
加 /i 表示如果 e: 没有 mp3 文件夹就自动新建一个,否则会有询问

posted @ 2010-06-22 11:20 Li Ya Qiang 阅读(733) | 评论 (0)编辑 收藏

来自http://www.blogjava.net/fingki/archive/2010/03/02/314268.html

在使用Iterator处理Collection时,注意java.util.ConcurrentModificationException。
1.如果你仅仅是对collection进行遍历查询,那么不必担心什么。
2.但如果你在遍历过程中要对collection进行删除,那么你就要注意了。
For example:
private void testDel() {  
  1.     List<String> list = new ArrayList<String>();  
  2.     for (int i = 0; i < 10; i++) {  
  3.         String str = "td" + i;  
  4.         list.add(str);  
  5.     }  
  6.   
  7.     for (Iterator it = list.iterator(); it.hasNext();) {  
  8.         String str = (String) it.next();  
  9.         if (str.equals("td5")) {  
  10.             // list.remove(str);  // 删除方法一 
  11.             it.remove();  // 删除方法二 
  12.         }  
  13.     }  

上面的代码运行没有问题,但如果你用“方法一”替代“方法二”,则会出现 java.util.ConcurrentModificationException。
(用for-each遍历也会出个类似问题)
具体原因是可以看一下先看看List中的remove方法源码:
  1. public boolean remove(Object o) {  
  2.     if (o == null) {  
  3.         for (int index = 0; index < size; index++)  
  4.             if (elementData[index] == null) {  
  5.                 fastRemove(index);  
  6.                 return true;  
  7.             }  
  8.     } else {  
  9.         for (int index = 0; index < size; index++)  
  10.             if (o.equals(elementData[index])) {  
  11.                 fastRemove(index);  
  12.                 return true;  
  13.             }  
  14.     }  
  15.     return false;  
  16. }  
  17.   
  18. private void fastRemove(int index) {  
  19.     modCount++; // 特别注意这里,这里只增加了modCount的值  
  20.     int numMoved = size - index - 1;  
  21.     if (numMoved > 0)  
  22.         System.arraycopy(elementData, index + 1, elementData, index,  
  23.                 numMoved);  
  24.     elementData[--size] = null; // Let gc do its work  

接着看。删除后得到下一个元素的代码,it.next():  it为AbstractList的内部类Iterator的一个实例。
  1. public E next() {  
  2.     checkForComodification();  
  3.     try {  
  4.         E next = get(cursor);  
  5.         lastRet = cursor++;  
  6.         return next;  
  7.     } catch (IndexOutOfBoundsException e) {  
  8.         checkForComodification();  
  9.         throw new NoSuchElementException();  
  10.     }  
  11. }  
  12.   
  13. final void checkForComodification() {  //注意这个方法
  14.     if (modCount != expectedModCount)  //检查这两个值是否相同
  15.         throw new ConcurrentModificationException();  

最后看Iterator的remove()方法的源代码:
  1. public void remove() {  
  2.     if (lastRet == -1)  
  3.         throw new IllegalStateException();  
  4.     checkForComodification();  
  5.     try {  
  6.         AbstractList.this.remove(lastRet);  
  7.         if (lastRet < cursor)  
  8.             cursor--;  
  9.         lastRet = -1;  
  10.         expectedModCount = modCount; // 设置expectedModCount  
  11.     } catch (IndexOutOfBoundsException e) {  
  12.         throw new ConcurrentModificationException();  
  13.     }  
  14. }  
  15.   
  16. final void checkForComodification() {  
  17.     if (modCount != expectedModCount)  
  18.         throw new ConcurrentModificationException();  

这下就明白了,list的remove方法只修改了modCount值,而iterator的remove能同步modCount和 expectedModCount.

posted @ 2010-03-02 16:50 Li Ya Qiang 阅读(203) | 评论 (0)编辑 收藏


posts - 10, comments - 0, trackbacks - 0, articles - 2

Copyright © Li Ya Qiang