第一篇:EXCEL使用心得
一、让格式自动添加固定的数字
例子:
大家知道,身份证号码的前6位,是省、市、区(县)的代号(如“340505”等),如果持证人是同一区(县)的,输入这样的的身份证号码,可以让“数字”标签帮你减轻输入的工作量:选中需要输入身份证号码的单元格(区域),打开“单元格格式”对话框,进入“数字”标签,在“分类”下面选中“自定义”选项,然后在右侧“类型”下面的方框中输入:“340505”@,确定退出。以后输入身份证号码7位及以后的数字(如“198903040611”)后,系统会自动在前面加上相应的代码,形成完整的身份证号码(如“***611”)。
二.教你使用Excel数组公式
Excel中数组公式非常有用,尤其在不能使用工作表函数直接得到结果时,数组公式显得特别重要,它可建立产生多值或对一组值而不是单个值进行操作的公式。
输入数组公式首先必须选择用来存放结果的单元格区域(可以是一个单元格),在编辑栏输入公式,然后按Ctrl+Shift+Enter组合键锁定数组公式,Excel将在公式两边自动加上花括号“{}”。注意:不要自己键入花括号,否则,Excel认为输入的是一个正文标签。
选取数组公式所占有的全部区域先选中区域中任意一个单元格,然后按下Ctrl+/键即可。编辑或删除数组公式编辑数组公式时,须选取数组区域并且激活编辑栏,公式两边的花括号将消失,然后编辑公式,最后按Ctrl+Shift+Enter键。选取数组公式所占有的全部区域后,按Delete键即可删除数组公式。
数组常量的使用数组公式中还可使用数组常量,但必须自己键入花括号“{}”将数组常量括起来,并且用“,”和“;”分离元素。其中“,”分离不同列的值,“;”分离不同行的值。
使用不在工作表中的数组有时,公式仅占用一个单元格时也需要以数组的方式输入。其具体原则是:一个公式使用了数组,并且这个数组不在工作表上,就应该使用数组的方式输入这个公式。
下面介绍两个使用数组公式的例子。
1.如需分别计算各商品的销售额,可利用数组公式来实现。
单元格F2中的公式为:{=SUM(IF(A2:A11=″商品1″,B2:B11*C2:C11,0))}。这个数组公式创建了一个条件求和,若在A2:A11中出现值“商品1”,则数组公式将B2:B11和C2:C11中与其相对应的值相乘并累加,若是其他值则加零。同时,虽然数组B2:B11和C2:C11均在工作表中,但其相乘的数组B2:B11*C2:C11不在工作表中,因此必须使用数组公式。
2.假设要将A1:A50区域中的所有数值舍入到2位小数位,然后对舍入的数值求和。很自然地就会想到使用公式:=ROUND(A1,2)+ROUND(A2,2)+…+ROUND(A50,2)。
有没有更简捷的算法呢?有。因为数组ROUND(A1:A50,2)并不在工作表中,因此要使用数组的方式输入公式,即:{=SUM(ROUND(A1:A50,2))}。
三、自动更正
1.从工具菜单中选择“自动更正”,打开自动更正对话框。
2.在“替换”框中输入数据,如:“4z”,在“替换为”框中输入数据,如:“枣阳市第四中学”,单击“添加”,再单击 “确定”。
之后,只需在单元格中输入“4z”两字,即会自动更正为“枣阳市第四中学”。
四、在excel工作表中输入计算公式时,如果想让储存格在显示计算结果和计算公式本身之间切换,您会采取什么方式呢?
是不是每次都从“工具”>“选项”>“视图”>“窗口选项”>“公式”来切换呢?有没有更简便的方法呢?
其实,我们可以利用“ Ctrl+` ”键来决定显示或隐藏公式,每按一次就可让储存格在显示计算的结果和计算公式本身之间自由切换。
五、快速录入文本文件中的内容
现在您手边假如有一些以纯文本格式储存的文件,如果此时您需要将这些数据制作成Excel XP的工作表,那该怎么办呢?重新输入一遍,太浪费时间;将菜单上的数据一个个复制到工作表中,同样也费事。这时!您只要在Excel XP中巧妙使用其中的文本文件导入功能,就可以大大减轻需要重新输入或者需要不断复制、粘贴的巨大工作量了。使用该功能时,您只要在Excel XP编辑区中,选定菜单栏中的“数据/获取外部数据/导入文本文件”命令,然后在导入文本会话窗口选择要导入的文本文件,按下“导入”钮以后,程序会弹出一个文本导入向导对话框,您只要按照向导的提示进行操作,就可以把以文本格式的数据转换成工作表的格式了。
六、行列转置
假如A1-A10单元格中有不同的内容,现在需要将这些内容分别排列在A1、B1、C1、D1...J1单元格中,即将原来在同一列中的内容重新排列在一行中。难道要一个一个单元格去复制粘贴吗?完全不用。
首先,选中A1-A10单元格,单击右键,在弹出的菜单中选择“复制”命令;接着单击B1单元格,再单击右键,在弹出的菜单中选择“选择性粘贴”命令,弹出对话框,选择其中的复选项“转置”,点击确定。这时你会看到B1、C1....K1单元格中已有了A1-A10单元格中的内容,将A列选中,在右键菜单中删除,此时行列转换工作就完成了。
七、在Excel2000中设计彩色数字
在你使用Excel2000对一张工作表中的数据进行处理时,有时是不是希望其中某些数据能够有自己特殊的显示格式?比如,现在你有如图的一张Excel工作表,在“总成绩”一栏中,你需要小于120的显示为蓝色,大于120的显示为红色。下述的方法,可以让你的愿望变为现实。该方法是:
1.选中D25的单元格区域。
2.单击“格式”菜单中的“单元格”命令,然后单击“数字”选项卡。
3.单击“分类”列表中的“自定义”选项,在“类型”框中键入“[蓝色][<120];[红色][>=120]”。
4.单击“确定”按钮。
怎么样,Excel按你的要求显示出不同颜色的数字了吧?
最后,对在“类型”框中键入的数字格式代码进行简单地说明,“[蓝色]”是对数据显示颜色的设置,除“红色”、“蓝色”外,还可使用六种颜色,它们是黑色、青色、绿色、洋红、白色、黄色。“[>=120]”是条件设置,可用的条件运算符有:>、<、>=、<=、=、<>。当有多个条件设置时,各条件设置以分号“;”间隔。
八、减少修改EXCEL参数的秘籍
在此处设计好的公式,拿到彼处用时,大部分不会完全合适,往往要修改公式中的参数.特别是函数中引用的单元格区域,往往需要修改.所以这里就以单元格区域为例,介绍一种减少或者是避免参数修改的办法.虽然说不上"万能",但将公式任意粘贴而基本不用修改是确实能办到的.
一个单元格、或者由许多单元格组成的单元格集合都可以作为一个区域,并可以命名一个名字。这许多朋友都知道。但对合理恰当地使用命名区域带来的方便,许多朋友或者是不重视,或者是觉得麻烦而较少使用。不过要实现上面的目标,我建议大家还是尽可能使用命名的区域。其好处如下:
1、直观易记,区域很多时,形式如(B2:M50)的名字既不好记忆,也难以一下子断定意义,反之,使用区域名字,特别是用中文作为区域名字时,能见文知义,大大减轻了记忆负
担。例如,将区域(B2:M50)命名为“三甲物理分”,一见名字就明白意思.
2、如果某一区域需要在多个公式中使用,采用区域命名会很方便。例如函数中需要引用“三甲物理分”这个区域时,可以直接拿它当参数.如果想得到那种一次设计,多次重用的“计算模板”,则更是非将区域命名不可。
3、如果区域的范围需要扩大或缩小,只需要将原来的名字重新命名一下,而原来使用的函数参数不必改动。例如,要统计上面区域中有效数字的个数,用的公式是:=COUNT(三甲物理分)(注意函数括号内的区域名字不用加双引号);当需要把该区域扩大或缩小时,可以先将原有的区域名字“三甲物理分”删除,然后重新选定合适的范围再次用这个名字命名,而所有以“三甲物理分”作参数的函数均不须修改而仍能使用。
乍一看这好像就不错了,其实,这还不算完善.
前已述及,当函数移到别的地方使用时,其参数一般需要修改。比如要用上面的公式计算二乙班物理成绩的有效数字个数时(这里假设你已经将相应区域命名为“二乙物理分”),则函数中用到区域参数又都要修改为“二乙物理分”。可以推知,即使是只修改这一处参数,在处理很多学科时(因为每个班级可能进行多个学科的考试),修改参数的工作量也很大,况且实际计算中往往同时使用多个公式,更导致参数修改的工作量成几倍增加。以某中学三个年级24个教学班为例,假如每个年级考试5个学科,要求计算出每班各个学科的最高分、平均分、整个年级的前百强学生等项目.这些活儿就是让你用上? 命名的法宝,手工修改参数也会磨坏你的手指!
怎样才能减少修改的工作量、甚至做到不修改参数就能用呢?这就得需要在函数内间接引用参数。请往下看
A B C三甲物理分 三乙物理分 三甲语文分AVERAGE(三甲物理分)=AVERAGE(三甲物理分)=AVERAGE(三甲物理分)AVERAGE(INDIRECT(A1))AVERAGE(INDIRECT(B1))AVERAGE(INDIRECT(C1))假设先设计好EXCEL工作表,将准备处理的数据区域都进行命名,并把名字依次输入到表中第一行的各个单元格,类似下表那样.为了对两种方法进行比较,我们先在A2单元格中输入公式:=AVERAGE(三甲物理分),可得出三甲班的物理平均分,结果也正确,缺点就是像上面说的,将公式粘贴在B2、C2单元格中时,括号中的参数并不会自动取出第一行里对应的名字,还需要用手工一一修改!如何让它能"自动"引用正确的参数、即能"自动"引用第一行对应单元格里的文字呢?可以使用函数INDIRECT().
在EXCEL中,函数INDIRECT()的作用比较特殊.其作用介绍如下:例如已知存放在A1单元格中的文字"三甲物理分"是一个区域名字,当用INDIRECT(A1)函数时,可以通过A1单元格获得对"三甲物理分"区域的引用.好!下面我们验证一下:请你在上表中的A3单元格中输入:=AVERAGE(INDIRECT(A1)),从得出的结果看,与A2单元格中使用的公式结果相同.从公式的组成看,多了函数INDIRECT(A1),省去了区域名字!注意,这就是激动人心的关键点了:当你用鼠标拖拽的办法向右边单元格粘贴这个公式后,会发现这些单元格中的公式已经"自动"地引用了相应区域的名字,你连一个参数也不用修改就得出了正确结果!??这不正是实现了我们苦苦追求的目标吗?怎么样,很爽吧?
感谢你有耐心看到这里,下面我再送你一个"秘密武器"
上面介绍的那个有功劳的函数是INDIRECT(),它是解决名字引用的,当要引用的单元格中是数值时,它就不管用了.能引用单元格数值的是另一个函数VALUE()。它的用法是:如果在A2单元格中存放有数字85,那么在A3单元格输入:=VALUE(A2),在A3中也能得到85这个数字。要只是这样的代换显然意义不大,但把它用在公式中后意义就大不一样了。看下表:第二行中的数字是该学科达到“优秀”的分
A B C
三乙物理分 三乙物理分 三甲语文分
80
=COUNTIF(INDIRECT(A1,),“$#@62;=”&VALUE(A2))
DIRECT(B1,),“$#@62;=”&VALUE(B2))=COUNTIF(IN A
=COUNTIF(INDIRECT(C1,),“$#@62;=”&VALUE(C2))
数线,我们的目的是:在第三行中根据该学科的分数线求出该学科达到优秀成绩的人数.由于不同学科划定优秀的分数线一般也不同.要是直接了当的话,在A3中使用公式=COUNTIF((INDIRECT(A1,),“$#@62;=85”)就可以,但这样用到B列又会遇到类似上面的修改参数问题。要也像上面那样能"自动"引用第二行中的分数线该多好啊!别急,把VALUE()函数用上就成了!我们把A3中的公式改成:=COUNTIF(INDIRECT(A1,),“$#@62;=”&VALUE(A2)).请你把这个公式向右面粘贴,可以发现,不用修改任何参数就能"自动"地引用正确的单元格了.
如果你能够熟练应用INDIRECT()和VALUE()这两个函数,再加上区域命名的法宝,会给你带来不小的方便!
至于制作能多次使用的计算"模板",我采用的是很懒也很容易的方法:将上一次用过的EXCEL文件用"另存为"作个备份,然后打开,只将原始数据清去,其他全部保留,就成了一个"模板".这样,只需要输入原始数据,立即会得到结果,免去了输入公式,设计格式等一大堆麻烦.
九、技巧1:给别人看,但不给别人动
辛辛苦苦地设计了一个数据库或者表格,却被别人毛手毛脚地搞乱了,是不是很恼火?如果 是私人文件还好,只要设个密码就可以了,偏偏这是要别人往里面填数据或者是要给大家参考的,往往由于他人的“不小心”,而导致自己要重做整个表格,这种事情不知道大家遇到没有,我可是遇到过,辛苦加班加点用了7天才设计好的表格,因为没做好防护措施,致使....哎,伤心往事,不说也罢!
现在,我教大家一个好办法,让别人只能看,不能动!
为了防止别人无意改动表格的内容(尤其是一些计算公式),我们必须把这些单元格设成“只读”!
把不需要保护的的单元格选定,单击右键,设置单元格,将保护标签中的锁定复选框清除,然后对该工作表设置保护。此时,锁定的单元格是只读的,刚才已被清除锁定复选框的单元则可以正常输入。当然,如果你连某些单元的内容也不想别人看到,在确定这些单元保护标签中的锁定复 选框是选中的情况下,再选择隐藏即可,这样将不显示这些单元其中的内容。但是你必须对工作表或工作簿实施保护后,你的保护和隐藏才有效。要保护工作表,可按以下选择:
[工具]→[保护]→[保护工作表]→选择密码,重复输入相同密码,这样,以后要进入这个工作表,只要输入密码即可。
技巧2:得到偶数的单元格的相加值
因为工作需要,要得到偶数的单元格的值相加之和,以下是具体的要求和思路:
要求:得到A2+A4+A6+A8+A10+A12+A14......之和,假如是少还好办,假如有数十个相加的话就不好办了,怎样才能用一个公式来搞定它呢???
思路:呵呵,我已得到答案了!先用一列来得到当前行的行号,你可在C1输入1,然后向下拖得到每一行的行号,再用一列来判断当前行是否为偶数行,输入公式:"=IF(INT(C1/2)=C1/2,A1,0)",然后再累加C列即可。
函数解析:其中的INT函数为判断C1/2是否为整数,如果C1是偶数C1/2当然是整数了,IF函数判断INT(C1/2)是否为偶数,如是,则取A列值,如果不是,就取0值。
看懂以上公式后,再教你一个更简单的方法:用ROW函数.ROW()可以得到当前行的行号,这样,判断当前行是否为偶数就不用再增加C列了,只要直接输入公式:"=IF(INT(ROW(?)=ROW()/2,A1,0)",向下拖动,累加即可。
技巧3:如何使Excel中数字计算自动四舍五入
目的:要对一个单元格中的数据(利用函数计算得出的)在它本身所在的单元格内进行四舍五入。
//* 假设B1单元格内容为:=if(A1$#@62;5,6234*.05)*//
1.如果B1单元此后不再加入其他运算,只要:
右键单击B1 → 设置单元格格式 → 小数位数调整到2位.或者单击B1,选择快捷菜单上的 "千分格式",再选择快捷菜单上的 "退一位小数位" 即可。
2.如果B1单元此后还要再加入其他运算,只要:
在B1单元,将原有内容加入ROUND函数即可:=round(if(A1$#@62;5,6234*.05),2)
其中,最后一位数"2"代表你想要数据参与计算的结果截止到小数点后两位,如果想要三位,直接改成"3"即可。
以上第一种方法只能达到显示上的四舍五入,当数据再次参与计算时,将不会以四舍五入后的数值参与。第二种方法,当数据再次参与计算时,将以四舍五入后的数值(即其显示在单元格中的数据)参与计算。
技巧4:将键入的阿拉伯数字自动转换成人民币大写金额
在使用EXCEL过程中,在制作财务凭证时经常需要将数字表示为大写的数字金额,可用设置单元格格式的方法来实现:
1.首先鼠标右键单击需要用大写金额显示的单元格。
2.(*假设此单元格金额为123.50元*)→ 设置单元格格式 → 数字 → 自定义 → 在类型框中输入 [DBNum2]0“百”0“拾”0“元”0“角”“整” 即可将选中的单元格中的数字显示为大写金额:(壹百贰拾叁元伍角整)。
(*假设此单元格金额为1234.51元*)→ 设置单元格格式 → 数字 → 自定义 → 在类型框中输入 [DBNum2]0“千”0“百”0“拾”0“元”0“角”0“分”“整” 即可将选中的单元格中的数字显示为大写金额:(壹千贰百叁拾肆元伍角壹分整)。
第二篇:Excle使用心得
EXCEL使用技巧
01、如何在已有的单元格中批量加入一段固定字符?
例如:在单位的人事资料,在excel中输入后,由于上级要求在原来的职称证书的号码全部再加两位,即要在每个人的证书号码前再添上两位数13,如果一个一个改的话实在太麻烦了,那么我们可以用下面的办法,省时又省力:
1)假设证书号在A列,在A列后点击鼠标右键,插入一列,为B列;
2)在B2单元格写入: =“13” & A2 后回车;
3)看到结果为 13xxxxxxxxxxxxx 了吗?鼠标放到B2位置,单元格的下方不是有一个小方点吗,按着鼠标左键往下拖动直到结束。当你放开鼠标左键时就全部都改好了。若是在原证书号后面加13 则在B2单元格中写入:=A2 & “13” 后回车。
02 用IF函数清除EXCEL工作表中的计算出现的0
=IF(K14*M14=0,“",K14*M14)该式所表示的含义为:如果单元格K14与M14内数值的乘积为零,那么存放计算结果的单元格显示为一个空白单元格;反之,单元格K14与M14内数值的乘机为不为零,这两个单元格的数值将被进行乘积运算。
06、在Excel中如何设置加权平均?
加权平均在财务核算和统计工作中经常用到,并不是一项很复杂的计算,关键是要理解加权平均值其实就是总量值(如金额)除以总数量得出的单位平均值,而不是简单的将各个单位值(如单价)平均后得到的那个单位值。在Excel中可设置公式解决(其实就是一个除法算式),分母是各个量值之和,分子是相应的各个数量之和,它的结果就是这些量值的加权平均值。
07、如果在一个Excel文件中含有多个工作表,如何将多个工作表一次设置成同样的页眉和页脚?如何才能一次打印多个工作表?
把鼠标移到工作表的名称处(若你没有特别设置的话,Excel自动设置的名称是“sheet1、sheet2、sheet3.......”),然后点右键,在弹出的菜单中选择“选择全部工作表”的菜单项,这时你的所有操作都是针对全部工作表了,不管是设置页眉和页脚还是打印你工作表。
15、如何快速选取工作表中所有包含公式的单元格?
有时,需要对工作表中所有包含公式的单元格加以保护,或填入与其他单元格不同的颜色,以提醒用户注意不能在有此颜色的区域内输入数据。以下方法可以帮助快速选取所有包含公式的单元格:选择“编辑”“定位”(F5),单击“定位条件”按钮,在“定位条件”对话框中选择“公式”项,按“确定”按钮即可。
16、如何在不同单元格中快速输入同一数内容?
选定单元格区域,输入值,然后按 Ctrl+ Ener键,即可实现在选定的单元格区域中一次性输入相同的值。
17、只记得函数的名称,但记不清函数的参数了,怎么办?
如果你知道所要使用函数的名字,但又记不清它的所有参数格式,那么可以用键盘快捷键把
参数粘贴到编辑栏内。
具体方法是:在编辑栏中输入一个等号其后接函数名,然后按 Ctr+ A键,Excel则自动进入“函数指南——步骤 2之2”。当使用易于记忆的名字且具有很长一串参数的函数时,上述方法显得特别有用。
27、如何快速地将数字作为文本输入?
在输入数字前加一个单引号“’”,可以强制地将数字作为文本输入。
35、如何使单元格中的颜色和底纹不打印出来?
对那些加了保护的单元格,还可以设置颜色和底纹,以便让用户一目了然,从颜色上看出那些单元格加了保护不能修改,从而可增加数据输入时的直观感觉。但却带来了问题,即在黑白打印时如果连颜色和底纹都打出来,表格的可视性就大打折扣。解决办法是:选择“文件”“页面设置”“工作表”,在“打印”栏内选择“单元格单色打印”选项。之后,打印出来的表格就面目如初了。
37、“$”的功用
Excel一般使用相对地址来引用单元格的位置,当把一个含有单元格地址的公式拷贝到一个新的位置,公式中的单元格地址会随着改变。你可以在列号或行号前添加符号 “$”来冻结单元格地址,使之在拷贝时保持固定不变。
38、如何用汉字名称代替单元格地址?
如果你不想使用单元格地址,可以将其定义成一个名字。
定义名字的方法有两种:一种是选定单元格区域后在“名字框”直接输入名字,另一种是选定想要命名的单元格区域,再选择“插入”“名字”“定义”,在“当前工作簿中名字”对话框内键人名字即可。使用名字的公式比使用单元格地址引用的公式更易于记忆和阅读,比如公式“=SUM(实发工资)”显然比用单元格地址简单直观,而且不易出错。
39、如何在公式中快速输入不连续的单元格地址?
在SUM函数中输入比较长的单元格区域字符串很麻烦,尤其是当区域为许多不连续单元格区域组成时。这时可按住Ctrl键,进行不连续区域的选取。区域选定后选择“插入”“名字”“定义”,将此区域命名,如Group1,然后在公式中使用这个区域名,如“=SUM(Group1)”。
42、工作表名称中能含有空格吗?
能。例如,你可以将某工作表命名为“Zhu Meng”。有一点结注意的是,当你在其他工作表中调用该工作表中的数据时,不能使用类似“= Zhu Meng!A2”的公式,否则 Excel将提示错误信息“找不到文件Meng”。解决的方法是,将调用公式改为“='Zhu Mg'!A2”就行了。当然,输入公式时,你最好养成这样的习惯,即在输入“=”号以后,用鼠标单由 Zhu Meng工作表,再输入余下的内容。
46、如何减少重复劳动?
我们在实际应用Excel时,经常遇到有些操作重复应用(如定义上下标等)。为了减少重复劳动,我们可以把一些常用到的操作定义成宏。其方法是:选取“工具”菜单中的“宏”命令,执行“记录新宏”,记录好后按“停止”按钮即可。也可以用VBA编程定义宏。
47、如何快速地批量修改数据?
假如有一份 Excel工作簿,里面有所有职工工资表。现在想将所有职工的补贴增加50(元),当然你可以用公式进行计算,但除此之外还有更简单的批量修改的方法,即使用“选择性粘贴”功能: 首先在某个空白单元格中输入50,选定此单元格,选择“编辑”“复制”。选取想修改的单元格区域,例如从E2到E150。然后选择“编辑”“选择性粘贴”,在“选择性粘贴”对话框“运算”栏中选中“加”运算,按“确定”健即可。最后,要删除开始时在某个空白单元格中输入的50。
48、如何快速删除特定的数据?
假如有一份Excel工作薄,其中有大量的产品单价、数量和金额。如果想将所有数量为0的行删除,首先选定区域(包括标题行),然后选择“数据”“筛选”“自动筛选”。在“数量”列下拉列表中选择“0”,那么将列出所有数量为0的行。此时在所有行都被选中的情况下,选择“编辑”“删除行”,然后按“确定”即可删除所有数量为0的行。最后,取消自动筛选。
49、如何快速删除工作表中的空行?
以下几种方法可以快速删除空行:
方法一:如果行的顺序无关紧要,则可以根据某一列排序,然后可以方便地删掉空行。方法二:如果行的顺序不可改变,你可以先选择“插入”“列”,插入新的一列入在A列中顺序填入整数。然后根据其他任何一列将表中的行排序,使所有空行都集中到表的底部,删去所有空行。最后以A列重新排序,再删去A列,恢复工作表各行原来的顺序。
方法三:使用上例“如何快速删除特定的数据”的方法,只不过在所有列的下拉列表中都选择“空白”。
50、如何使用数组公式?
Excel中数组公式非常有用,它可建立产生多值或对一组值而不是单个值进行操作的公式。要输入数组公式,首先必须选择用来存放结果的单元格区域,在编辑栏输入公式,然后按ctrl+Shift+Enter组合键锁定数组公式,Excel将在公式两边自动加上括号“{}”。不要自己键入花括号,否则,Excel认为输入的是一个正文标签。要编辑或清除数组公式.需选择数组区域并且激活编辑栏,公式两边的括号将消失,然后编辑或清除公式,最后按Ctrl+shift+Enter键。
52、在Excel中用Average函数计算单元格的平均值的,值为0的单元格也包含在内。有没有办法在计算平均值时排除值为0的单元格?
方法一:如果单元格中的值为0,可用上例“0值不显示的方法”将其内容置为空,此时空单元格处理成文本,这样就可以直接用Average函数计算了。
方法二:巧用Countif函数 例如,下面的公式可计算出b2:B10区域中非0单元格的平均值: =sum(b2: b10)/countif(b2: b1o,”<>0")
三、让不同类型数据用不同颜色显示
在工资表中,如果想让大于等于2000元的工资总额以“红色”显示,大于等于1500元的工资总额以“蓝色”显示,低于1000元的工资总额以“棕色”显示,其它以“黑色”显示,我们可以这样设置。
1.在工作簿中,选中“工资总额”所在列,执行“格式→条件格式”命令,打开“条件
格式”对话框。单击第二个方框右侧的下拉按钮,选中“大于或等于”选项,在后面的方框中输入数值“2000”。单击“格式”按钮,打开“单元格格式”对话框,将“字体”的“颜色”设置为“红色”。(在Excle07中 开始----样式---条件格式 下面设置)
2.按“添加”按钮,并仿照上面的操作设置好其它条件(大于等于1500,字体设置为“蓝色”;小于1000,字体设置为“棕色”)。
3.设置完成后,按下“确定”按钮。
第三篇:CAD使用心得之一
CAD使用心得之一--CAD使用的三个基本方面:清晰、准确、高效
(2012-07-02 10:49:16)
很多CAD的教材,如果对照着学习的话,确实都能够在一定程度上掌握这个软件,如果到工作岗位,也都能勉勉强强的开始画图。但是,这远远不够,从书本到实战,还有一大段距离。因此,将收集的有关于使用CAD的一系列心得体会发出来与大家分享。
CAD使用心得连载之一
——CAD使用的三个基本方面:清晰、准确、高效
目前,设计公司的设计文件,特别是图纸,都是用CAD软件绘制的,但是还有很多人对CAD并不是非常熟悉,或者说使用起来并非得心应手,以至于效率并不是很高,可以说,绘制同样的一张图纸,速度快的和慢的在耗时上可能会相差好几倍。同时,每个人绘制出来的图纸看上去感觉都不尽相同:有些图纸看上去一目了然、清晰漂亮,而有些图纸不但表达不清,甚至可以用惨不忍睹来形容。
不知大家认为,使用CAD画图最重要的是什么?对这个问题,每个人都有可能理解不同,但在我看来,最重要的是时时刻刻记住自己使用CAD画图的目的是什么。
我们进行工程设计,不管是什么专业、什么阶段,实际上都是要将某些设计思想或者是设计内容,表达、反映到设计文件上。而图纸,就是一种直观、准确、醒目、易于交流的表达形式。所以我们完成的东西(不管是最终完成的设计成果,还是作为条件提交给其它专业的过程文件,一定需要能够很好的帮助我们表达自己的设计思想、设计内容。
有了这个前提,我们就应该明白,好的CAD图纸应该具有以下两个特征:清晰、准确。清晰,就是需要表达的东西必须清楚明了。好的图纸,看上去一目了然。构件表达、尺寸标注、文字说明清清楚楚,互不重叠„„除了图纸打印效果清晰以外,在屏幕上的显示也必须清晰。图面清晰除了能清楚表达设计思路和设计内容外,也是提高绘图速度的基础。准确,就是标注不能错误,指示不能模糊。制图准确不仅是为了好看,更重要的是可以直观的反映一些图面问题,对于提高绘图速度也有重要的影响,特别是在图纸修改时。我们在使用CAD绘图时,无时无刻都应该把以上两点铭刻在心。只有做到这两点,才能说在绘图方面基本过关。
图面表示要“清晰”、“准确”,而在绘图过程中,还有同样重要的一点,就是“高效”。能够高效绘图,好处不用多说。
清晰、准确、高效是CAD软件使用的三个基本点。在CAD软件中,除了一些最基本的绘图命令外,其他的各种编辑命令、各种设置定义,可以说都是围绕着清晰、准确、高效这三方面来编排的。我们在学习CAD中的各项命令、各种设置时,都要思考一下,它们能在这三个方面起到那些作用;在使用时应该注重什么;在什么情况和条件下,使用这些命令最为合适。
第四篇:STM32使用心得
stm32使用心得
第一次使用stm32,以前用过
51、avr、pic、2812,感觉stm32还真有点不一样,呵呵。
因为是第一次使用,下面说的肯定有不少错误,诚心求大家指正。
这次做的是用stm32f103zd+lattice 的lc4256v做一个波形发生器。通过上位机可以控制生成波形的频率,然后stm32根据频率计算波形占空比数据,通过总线形式传给cpld,然后cpld把这些数据转换成相对应占空比的pwm输出,外部接RC滤波电路,产生相对应的波形。由于频率范围较大,计算量也比较大,所以采用了stm32+cpld的结构。Stm32运行在72MHZ,通过mco脚给cpld 36M HZ的时钟,stm32和cpld通过总线方式通信。
此系统中Stm32主要用到的资源是:一个UART,一个TIMER及其中断,FSMC和DMA。
本人总结了下,Stm32初始化一个片内外设一般过程一般有以下几部分:
1.InitStructure配置及初始化
2.时钟使能
3.相对应的IOInitStructure配置及初始化
4.相对应的IO时钟使能
5.外设使能
6.中断配置及中断程序编写
下面介绍一下自己所用的UART、TIMER、FSMC、DMA的初始化。
UART初始化:
此系统中使用的是UART2,未用UART中断。UART初始化主要有:IO初始化,UART InitSturcture初始化,UART时钟使能,UART使能。程序如下: GPIO_InitTypeDef GPIO_InitStructure;
// Configure USART2_Tx as alternate push-pull
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_2;
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP;
GPIO_Init(GPIOA, &GPIO_InitStructure);
// Configure USART2_Rx as input floating
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_3;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IN_FLOATING;
GPIO_Init(GPIOA, &GPIO_InitStructure);
//IO时钟使能
RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA, ENABLE);
USART_InitTypeDef USART_InitStructure;
/* USART2 configured as follow:
-BaudRate = 9600 baud
-Word Length = 8 Bits
-One Stop Bit
-No parity
-Hardware flow control disabled(RTS and CTS signals)
-Receive and transmit enabled
*/
USART_InitStructure.USART_BaudRate = 9600;
USART_InitStructure.USART_WordLength = USART_WordLength_8b;USART_InitStructure.USART_StopBits = USART_StopBits_1;
USART_InitStructure.USART_Parity = USART_Parity_No;
USART_InitStructure.USART_HardwareFlowControl = USART_HardwareFlowControl_None;
USART_InitStructure.USART_Mode = USART_Mode_Rx | USART_Mode_Tx;
/* Configure the USART2*/
USART_Init(USART2, &USART_InitStructure);
//UART时钟使能
RCC_APB1PeriphClockCmd(RCC_APB1Periph_USART2, ENABLE);
/* Enable the USART2 */
USART_Cmd(USART2, ENABLE);
TIMER初始化
使用的是TIM2。初始化主要包括TIM2 InitSturcture初始化,时钟使能,TIM2开启,中断配置,及中断服务程序编写。此TIM2作用主要是给DMA提供时钟,DMA在TIM2 UP时启动一次DMA发送过程。TIM2程序如下:
TIM_TimeBaseInitTypeDefTIM_TimeBaseStructure;
//定时器2
RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM2, ENABLE);
TIM_TimeBaseStructure.TIM_Period = 33;
TIM_TimeBaseStructure.TIM_Prescaler = 71;
TIM_TimeBaseStructure.TIM_ClockDivision = 0;
TIM_TimeBaseStructure.TIM_RepetitionCounter = 0x0;
TIM_TimeBaseStructure.TIM_CounterMode = TIM_CounterMode_Up;
TIM_TimeBaseInit(TIM2, &TIM_TimeBaseStructure);
TIM_ClearFlag(TIM2,TIM_FLAG_Update);
TIM_ARRPreloadConfig(TIM2,ENABLE);
TIM_ITConfig(TIM2,TIM_IT_Update,ENABLE);
TIM_Cmd(TIM2, ENABLE);
//中断配置
/* Enable the TIM2 gloabal Interrupt */
NVIC_InitStructure.NVIC_IRQChannel = TIM2_IRQChannel;
NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 0;
NVIC_InitStructure.NVIC_IRQChannelSubPriority = 1;
NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;
NVIC_Init(&NVIC_InitStructure);
//定时器2中断服务程序
void TIM2_IRQHandler(void)//这个函数可以在文件stm32f10x.c文件中查找到 {
TIM_ClearITPendingBit(TIM2,TIM_IT_Update);
}
FSMC初始化
FSMC主要用来和CPLD进行总线通信,由DMA方式发送,在TIM2计时时间到后启动一次DMA发送,发送的数据由已计算好的数组中的一个16位数据以16位方式发给FSMC的地址。由于此系统电路已固定,stm32与CPLD间数据线是8位,故在向FSMC地址写16位数据时,FSMC会将数据拆成2部分发送。本人在实际编程时发现,如向*(volatile u16*)(Bank1_NOR4_ADDR+0x40)地址给CPLD写16位数据时,会在40h接收到低8位数据,在41h接收到高8位数据。按道理来说这些数据应该与NBL0, NBL1信号有关,本人在CPLD编程时未理会这个,具体时序不是很清楚,有待考究。
FSMC初始化程序如下:
FSMC_NORSRAMInitTypeDefFSMC_NORSRAMInitStructure;
FSMC_NORSRAMTimingInitTypeDefp;
p.FSMC_AddressSetupTime = 3;//6
p.FSMC_AddressHoldTime = 0;//3
p.FSMC_DataSetupTime = 8;//25
p.FSMC_BusTurnAroundDuration = 0;
p.FSMC_CLKDivision = 0;
p.FSMC_DataLatency = 0;
p.FSMC_AccessMode = FSMC_AccessMode_A;
FSMC_NORSRAMInitStructure.FSMC_Bank = FSMC_Bank1_NORSRAM4;FSMC_NORSRAMInitStructure.FSMC_DataAddressMux = FSMC_DataAddressMux_Disable;
FSMC_NORSRAMInitStructure.FSMC_MemoryType = FSMC_MemoryType_SRAM;
FSMC_NORSRAMInitStructure.FSMC_MemoryDataWidth = FSMC_MemoryDataWidth_8b;
FSMC_NORSRAMInitStructure.FSMC_BurstAccessMode = FSMC_BurstAccessMode_Disable;
FSMC_NORSRAMInitStructure.FSMC_WaitSignalPolarity = FSMC_WaitSignalPolarity_Low;
FSMC_NORSRAMInitStructure.FSMC_WrapMode = FSMC_WrapMode_Disable;
FSMC_NORSRAMInitStructure.FSMC_WaitSignalActive = FSMC_WaitSignalActive_BeforeWaitState;
FSMC_NORSRAMInitStructure.FSMC_WriteOperation = FSMC_WriteOperation_Enable;
FSMC_NORSRAMInitStructure.FSMC_WaitSignal = FSMC_WaitSignal_Disable;
FSMC_NORSRAMInitStructure.FSMC_ExtendedMode = FSMC_ExtendedMode_Disable;
FSMC_NORSRAMInitStructure.FSMC_AsyncWait = FSMC_AsyncWait_Disable;
FSMC_NORSRAMInitStructure.FSMC_WriteBurst = FSMC_WriteBurst_Disable;
FSMC_NORSRAMInitStructure.FSMC_ReadWriteTimingStruct = &p;FSMC_NORSRAMInitStructure.FSMC_WriteTimingStruct = &p;
FSMC_NORSRAMInit(&FSMC_NORSRAMInitStructure);
RCC_AHBPeriphClockCmd(RCC_AHBPeriph_FSMC, ENABLE);
FSMC_NORSRAMCmd(FSMC_Bank1_NORSRAM4, ENABLE);
//IO初始化
GPIO_InitTypeDef GPIO_InitStructure;
RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOD | RCC_APB2Periph_GPIOG | RCC_APB2Periph_GPIOE |
RCC_APB2Periph_GPIOF, ENABLE);
/*--GPIO Configuration-----------------------*/
/* SRAM Data lines configuration */
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_0 | GPIO_Pin_1 | GPIO_Pin_8 | GPIO_Pin_9 |
GPIO_Pin_10 | GPIO_Pin_14 | GPIO_Pin_15;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP;
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_Init(GPIOD, &GPIO_InitStructure);
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_7 | GPIO_Pin_8 | GPIO_Pin_9 | GPIO_Pin_10 |
GPIO_Pin_11 | GPIO_Pin_12 | GPIO_Pin_13 | GPIO_Pin_14 |
GPIO_Pin_15;
GPIO_Init(GPIOE, &GPIO_InitStructure);
/* SRAM Address lines configuration */
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_0 | GPIO_Pin_1 | GPIO_Pin_2 | GPIO_Pin_3 |
GPIO_Pin_4 | GPIO_Pin_5 | GPIO_Pin_12 | GPIO_Pin_13 |GPIO_Pin_14 | GPIO_Pin_15;
GPIO_Init(GPIOF, &GPIO_InitStructure);
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_0 | GPIO_Pin_1 | GPIO_Pin_2 | GPIO_Pin_3 |
GPIO_Pin_4 | GPIO_Pin_5;
GPIO_Init(GPIOG, &GPIO_InitStructure);
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_11 | GPIO_Pin_12 | GPIO_Pin_13;GPIO_Init(GPIOD, &GPIO_InitStructure);
/* NOE and NWE configuration */
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_4 |GPIO_Pin_5;
GPIO_Init(GPIOD, &GPIO_InitStructure);
/* NE4 configuration */
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_12;
GPIO_Init(GPIOG, &GPIO_InitStructure);
/* NBL0, NBL1 configuration */
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_0 | GPIO_Pin_1;
GPIO_Init(GPIOE, &GPIO_InitStructure);
此处简单介绍一下FSMC总线方式的使用。
FSMC初始化完了之后,进行如下定义,#define Bank1_NOR4_ADDR((u32)0x6c000000)
#define cs_sin*(volatile u16*)(Bank1_NOR4_ADDR+0x40)
然后cs_sin=1000就是往这个地址写数字1000=0x03e8,则cpld 40h地址收到数据为0xe8,41h收到的数据为0x03
i=cs_sin,就是读这个地址的数据,由于定义的是16位的数据地址,故读到的数据是40h为低8位数据,41h为高8位数据
DMA初始化:
DMA在TIM2 UP时触发,将已经计算好放在数组dat_tocpld的16位数据发送到fsmc地址为(Bank1_NOR4_ADDR+0x40)的空间。
初始化程序如下:
DMA_InitTypeDef DMA_InitStructure;
DMA_DeInit(DMA1_Channel2);
RCC_AHBPeriphClockCmd(RCC_AHBPeriph_DMA1, ENABLE);
/* Enable TIM2 DMA interface */
TIM_DMACmd(TIM2, TIM_DMA_Update, ENABLE);
DMA_InitStructure.DMA_PeripheralBaseAddr =(u32)(Bank1_NOR4_ADDR+0x
40);
DMA_InitStructure.DMA_MemoryBaseAddr =(u32)dat_tocpld;
DMA_InitStructure.DMA_DIR = DMA_DIR_PeripheralDST;
DMA_InitStructure.DMA_BufferSize = 1152;
DMA_InitStructure.DMA_PeripheralInc = DMA_PeripheralInc_Disable;DMA_InitStructure.DMA_MemoryInc = DMA_MemoryInc_Enable;
DMA_InitStructure.DMA_PeripheralDataSize =DMA_PeripheralDataSize_HalfWord;
DMA_InitStructure.DMA_MemoryDataSize = DMA_MemoryDataSize_HalfWord;DMA_InitStructure.DMA_Mode = DMA_Mode_Circular;
DMA_InitStructure.DMA_Priority = DMA_Priority_High;
DMA_InitStructure.DMA_M2M = DMA_M2M_Disable;
DMA_Init(DMA1_Channel2, &DMA_InitStructure);
/* Enable DMA1 Channel2 */
DMA_Cmd(DMA1_Channel2, ENABLE);
最后附上源自http://sxqstudy.blog.163.com/blog/static/***03148709/介绍的关于PWM电压转换电路。
在PWM用于DA转换的场合,阻容滤波电路是关系转换效果的重要环节。
由RC充放电常数我们可以大致计算出阻容环节的充放电频率,一般为了得到理想的滤波效果,这个频率要远小于PWM的输出频率(小于四分之一)。
一般情况下,当C较小R较大时,DA转换出的电压损耗很小,但是纹波却很大;当C较大R较小时,DA转换出的电压损耗很大,但纹波相对较小。
所以当需要进行线形度很高的精确DA转换时必须使用较小的滤波电容,且尽量避免使用电解类电容。而为了得到较强的信号输出,RC惯性环节之后还必须加一级高性能的电压跟随,然后在跟随器输出的地方加上一个滤波用的电解电容,用于平滑RC惯性环节的纹波。但是这还不够,因为这时的输出电压里可能含有较多的交流谐波成分,如果处理不当,跟随器有可能自激。解决的办法就是使用一个小的去藕电容。而且这里电容的放置顺序必须是电解电容在前,去藕电容在后!
如果输出电压精度和线形度要求不高,但是对纹波要求却很高,或者这个电压比较固定时,可以使用电容较大的滤波组合。因为,虽然大电容的直流损耗较大,但是我们可以通过调节PWM占空比来达到要求的输出电压,或者通过一级AD转换的反馈来实现精确的固定电压输出。只是这里仍然要加一级电压跟随器,以便于后级采集电路使用,且AD采集点放置在跟随器输出处。
第五篇:430使用心得
学习MSP430G2553,已有7天有余。个人觉着:低功耗是其最大亮点。为此可谓是处心积虑。因而中断/低功耗模式在430的应用中便显得千娇百媚,楚楚动人!这里,先跟大伙看下这个中断的情况。
#include
WDTCTL = WDTPW + WDTHOLD;//禁止看门狗计数 P1DIR=BIT0+BIT1;//P1.01设置为输出,P1.4/5是输入 P1OUT=BIT0+BIT1+BIT4+BIT5;//P1.01为高,P.4/5上拉 P1REN=BIT4+BIT5;//P1.4上拉使能 P1IE=BIT4+BIT5;//P1.4开中断 P1IES=BIT4+BIT5;//中断沿选择 __enable_interrupt();//开总中断 while(1);//没事做 }
#pragma vector=PORT1_VECTOR
__interrupt void PORT1()//P1口中断服务程序 {
unsigned int i=0;unsigned char PushKey=0;
PushKey=P1IFG&(BIT4+BIT5);//读取是哪个键按下 for(i=0;i<65535;i++);//延时后再作判断,避免是抖动 if(!(P1IN&PushKey))//没有按下,则为抖动,标志清零 P1IFG=0;
if((P1IN&PushKey))//判断是否有键按下 {
for(i=0;i<65535;i++);if((P1IN&PushKey)){ if((PushKey&BIT4))P1OUT^=BIT0;if((PushKey&BIT5))P1OUT^=BIT1;}
P1IFG&=~(BIT4+BIT5);} }
这个程序,最出彩的地方在于“while(1);”这个等待的语句。
中断没发生前,程序在停这儿等待,就相当于CPU一直停在儿没事做歇着,也许是在等待戈多。一旦中断条件发生,在这里是按键,它便好像逮着什么似的,便进入中断,去执行中断程序中的代码。
这里,我们可见。中断没来之前,CPU它无所事事,却没有关闭,仍在耗电。中断来了之后,它赶忙地处理中断程序。前前后后,他总在折腾。肯定累得够戗。
那CPU在哪段时间内本可好好休息,不必浪费精力呢???大伙都知道,肯定是等待戈多那个时间里。所以便会让它在等待戈多的时间里去休眠。中断来了确实需它出面处理时,它再醒来处理中断事件,更为妥当!!于是乎,便有了下面的程序。#include
这里最大与上面最大的不同就是,用LPM3;替代了上面的While(1);这样一来,在中断没来之前,CPU不再作无谓的等待而耗电,而是处在休眠状态里。中断发生后,CPU便会自动唤醒,进入中断去处理中断程序。实现了低功耗的目的。
这里的低耗模式的实现是这样的,中断程序中是唤醒CPU,而后进入主程序,执行相应的功能模块。相应的功能模块,全在主程序中。
这便是所谓的中断中只用唤醒用。我们可以采用另一种方式,主程序中断只用休眠用。且看下面程序。
#include
TACTL=TASSEL1+MC1+TACLR;//定时器时钟源为SMCLK,up,不分频,清零 CCTL0|=CCIE;//使能比较器中断 CCR0=50000;//计数器终值 P1DIR=0xff;//P1输出口 __enable_interrupt();//使能全局中断,C编译器中的内部函数 LPM3;} #pragma vector=TIMER0_A0_VECTOR __interrupt void Timer(void){ if(flag==0){ i++;if(i==10)//定时0.5s { i=0;P1OUT^=table[num++];P1OUT=table[num];} if(num==8)flag=1;} if(flag==1){ i++;if(i==10)//定时0.5s { i=0;P1OUT^=table[num--];P1OUT=table[num];} if(num==0)flag=0;} }
这里,主程序中只用休眠,一旦中断条件发生,则进入中断,而进入中断后,CPU便自动唤醒。因为要处理中断服务程序。不过,中断完了之后,会恢复到中断前的状态,在这里便又回到了休眠状态。
休眠的写法中,有一个点要注意。若主函数中只作休眠,则中断函数中不必写唤醒的语句;若中断中只作唤醒,则主函数中休眠+待执行语句,要用循环。
相信通过这里的讲解,大伙已明白低功耗和中断的关系了吧。明白了中断为什么在430中犹为重要了吧
先说说添加自定义头文件的方法和注意事项
方法的话,随便一本MSP430单片机C程序设计书中都有详细详解,我就不多说了。
最要注意的是添加头文件了,也许你们也知道“#include<>”和“#include“””都可以添加头文件,挡在添加自己个人头文件时,它们又有神马区别呢,你们就不知道了吧。呵呵,现在说明一下:放在自己工程目录下的头文件要用#include “xxxxx.h” ,系统目录下的头文件才用#include
怎么判断头文件的数值(如0x0001)是表示十六进制数还是表示地址?
1、#define BIT0(0×0001)//(0×0001)不是地址,而是一个16进制数值。
例
1、P3DIR |= BIT3;实际上也可以写成P3DIR |= 0×0008;意思是将P3口的默认上电值0×0000和0×0008相与,设置P3口的第三位(即P3.3)管脚作输出使用。例
2、WDTCTL = WDTPW + WDTHOLD;实际上就是WDTCTL=0×5A80;
你可以在头文件中查到#define WDTPW(0×5A00)和#define WDTHOLD(0×0080)。WDTCTL是看门狗的控
制寄存器,在msp430的User’Guide中有说明:当它的值为0×5A80时停止看门狗定时。
那为什么我们不直接写成WDTCTL=0×5A80;呢?这样的话程序的可读性会很差。0×5A80只是一个数值,当你下次再看你写的程序,或者别人读你的程序时,就不明白WDTCTL=0×5A80;的
意思了。如果写成WDTCTL = WDTPW + WDTHOLD;就好理解多了:
WDTPW(Watchdog timer password,看门狗的密码,WDTCTL的高8位):只有WDTCTL的高8位为
0×5A时才能对WDTCTL寄存器进行写操作。
WDTHOLD(Watchdog timer hold,WDTCTL的第7位):当WDTCTL的第7位为1时,停止看门狗计时。
这样我们通过PW,HOLD就可以轻松的知道WDTCTL = WDTPW + WDTHOLD;是做什么的了。可以看出
msp430的头文件是很人性化的。
2、当然也有表示地址的,例如,头文件中有以下部分:
#ifdef __IAR_SYSTEMS_ASM__ #define DEFC(name, address)sfrb name = address #define DEFW(name, address)sfrw name = address;//运用了可变参数宏的宏定义格式:#define 宏符号名(参数表)宏体;宏体中就是写出参数表中各个参数之间的关系。
#endif ……
#define P6OUT_(0×0035)DEFC(P6OUT , P6OUT_)//这里就是用了以上的可变参数宏。DEFC(P6OUT , P6OUT_)就表示:sfrb P6OUT = P6OUT_ //这里的0×0035就是指P6OUT这个寄存器的地址了。
1、#define ME1_(0x0004)DEFC(ME1 , ME1_)
me1关联端口0x0004 DEFC的C是字节的意思,也就是me1 就是地址0004处的一个字节即八位数据
2、#define FCTL1_(0x0128)DEFW(FCTL1 , FCTL1_)
其功能是从指定地址开始,定义若干个16位数据
对于对DEFC和DEFW的理解可以到#include
实质上就是要对sfrb和sfrw关键字的理解,下面就说说在C430中所扩展的关键字吧。
使用处理器专用扩展的保持可可移植性的 #pragma 伪指令
一、新增数据类型:
1、Sfrb----字节类型的特殊功能寄存器或外围模块
2、Sfrw----字类型的特殊功能寄存器或外围模块
3、Pointer--指针
4、Enum-----枚举
1、外围模块变量Sfrb、Sfrw也称作特殊功能寄存器变量,直接位于内部RAM单元。Sfrb范围为:0X00---OXFF; Sfrw范围为:0X100---0X1FF;
外围模块变量使符号名与此范围的字节或字相联系,该地址处寄存器可以符号化被寻址,但没有分配存储空间。
例如:
Sfrb P1IES =0X24H;字节是8位 Sfrb P1DIR = 0X22H;
Sfrw ADC12CTL1 =0X01A2H 字是16位
经过定义后就可以直接通过对应的符号访问这些寄存器了。
PIDIR = 0X01;P1.0输出
2、指针变量
IAR C430的指针变量包括代码指针和数据指针,都可以指向0000H---0FFFFH的范围的存储空间。
3、枚举类型
用enum关键字,可以声明的每一个变量具有适合它的值所需的最短正数类型,可以是char、short、int或long。
二、中断函数定义
#pragma vector = 中断矢量变量
_interrupt void 函数名(void){
调用函数声明
函数变量定义
函数执行语句 }
其中 _interrupt说明了是中断函数,中断矢量变量:说明了该中断服务函数对应的中断向量表中的中断地址
例如:
#pragma vector = WDT_VECTOR()
_interrupt voidwatchdog_timer(void){
P1OUT ^= 0X01;
}
四、提高IAR C430 代码的效率
1、仅在保存数据存储器空间的时候才使用位域
2、尽可能使用无符号类型,unsigned类型
3、对16位数据类型MSP430的工作效率更高,通常8位数据类型的使用可节省数据空间,但是不减少代码大小,不支持32数据类型。
4、复制struct和union是耗费较大的操作,应避免运行时struct/union的赋值,带struct/union参数的函数以及返回struct/union的函数,应尽量采取指向struct/union的指针操作。
五、IAR头文件,用户程序通过头文件访问库定义,头文件使用#include伪指令与之相结合,为了避免浪费编译时间,定义被划分到许多不同的头部定义,每一个文件覆盖特定的函数区域,用户可以根据使用的内容选择不同的头文件。
IAR调试环境提供了MSP430单片机各系列的标准头文件,定义了系列中包含的寄存器的物理地址,在程序中可以字节使用寄存器名或者寄存器中位的名称,这样就避免使用实际的物理地址,使程序设计简介、高效。
六、IAR C430 的汇编语言接口 IAR C430 编译器可以把编译好的c语言模块与汇编语言模块链接起来,这对于要求代码效率较高的场合尤为重要。
通常用汇编语言来写子程序,并由C语言主函数调用
1、调用规则:
编译器使用两组寄存器
R12——R15用于传递参数,在调用时不加保护
其它通用寄存器R4---R---11主要用于存放寄存器变量和中间结果,在调用时应予以保护
2、堆栈结构和参数传递
每次调用子程序都会创建一个堆栈结构
3、从c程序传递参数
传递给汇编子程序的参数依照从右向左的次序。最左边的两个参数用寄存器传递,除非它们被定义成struct或union而使用堆栈传递。其余参数总是通过堆栈传递。