Perl与JS的比较(子程序)
子程序在不同的语言里有多种叫法,如过程、函数、方法。
一、子程序定义及调用
Perl定义使用关键字sub,调用子程序使用&。JS使用function定义,调用使用小括号()。
1 2 3 4 | sub sayHi { print 'Hi, everybody!' ; } &sayHi |
JS
1 2 3 4 | function sayHi() { alert( 'Hi, everybody!' ) } sayHi() |
二、返回值
两者不显示使用return时都具有默认返回值,Perl是undef,JS是undefined。除此之外,Perl在返回确切的数据时可以省略return。其它情形和JS一样,比如在分支中提前返回。
1 2 3 4 5 6 | $a = 3; $b = 5; sub sum { $a + $b ; # 这里不需要写return } print &sum ; # 8 |
JS
1 2 3 4 5 6 | var a = 3 var b = 5 function sum() { return a + b } alert(sum()) // 8 |
三、参数
上面示例的数字相加没有实际意义,每次传不同的参数才有用。
Perl中定义参数与JS很不同,它没有小括号,它大括号内部的$_与JS的arguments很象。如下
1 2 3 4 | sub sum { $_ [0] + $_ [1]; } print &sum (2, 4); |
JS
1 2 3 4 | function sum(a, b) { return a+b } alert(sum(2, 4)) |
如果不想使用索引方式,Perl还在子程序内部提供了一个“@_”,它是一个列表,存储了调用时的实际参数。
1 2 3 4 | sub sum { print @_ ; } &sum ( 'hello,' , 'world.' ); |
四、Perl和JS的子程序都有副作用,它们可以改变全局变量
五、私有、局部变量
Perl的子程序内使用my定义的是私有变量,JS则可以使用var定义。
1 2 3 4 5 6 | $num = 1; sub fun { my $num = 3; } print $num ; # 1 print &fun ; # 3 |
JS
1 2 3 4 5 6 7 | var num = 1 function fun() { var num = 3 return num } alert(num) // 1 alert(fun()) // 3 |
Perl中的关键字my除了在子程序内使用,还可以在语句块(if, while, foreach)中使用,具有块级作用域。JS的“var声明”则不具有。
1 2 3 4 5 6 | if ( my $a = 'hello' , defined ( $b )) { print $b ; } else { print $a ; } print $a ; # 执行时报错,$a只能在if语句块中使用 |
这里if语句中定义了局部变量b未定义,使用defined函数判断,会进入else中。最终打印“hello”。在if外再打印$a会报错,提示未定义。如果需要定义多个局部变量,Perl中需要使用小括号括起来,JS只需要用逗号分割。
1 2 3 | sub sum { my ( $a , $b ) = (1, 2); } |
注意,如下声明的只有$a是局部的
1 | my $a , $b ; |
在JS中不具有块级作用域,因此语句中使用var定义的变量会溢出到外层闭包。如下
1 2 3 4 | for ( var i=0; i<10; i++) { alert(i) } alert(i) |
打印0-9,有人可能期望i只能在for语句块内(大括号)使用,实际上JS中i在for外面也可以被引用,如果这一段不是写在function内,这个i则是全局变量。这也被认为是JS设计不当之处。
ES6中增加了一个let关键字可用来实现块级作用域,即可在function内可用,也可在for等语句中使用。
1 2 3 4 5 6 7 8 9 10 11 12 | <script type= "application/javascript;version=1.7" > var i = 1 function sum(a) { let i = 2 return i * a } for ( let i = 0; i < 10; i++) { console.log(i) } sum(10) alert(i) </script> |
分别在全局,函数sum内,for语句块内声明了同名的变量i,可以看到它们互不影响。最后alert显示的仍然是全局的i。需注意以上代码需在Firefox浏览器中运行。目前Firefox,Chrome支持let。
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· go语言实现终端里的倒计时
· 如何编写易于单元测试的代码
· 10年+ .NET Coder 心语,封装的思维:从隐藏、稳定开始理解其本质意义
· .NET Core 中如何实现缓存的预热?
· 从 HTTP 原因短语缺失研究 HTTP/2 和 HTTP/3 的设计差异
· 周边上新:园子的第一款马克杯温暖上架
· 分享 3 个 .NET 开源的文件压缩处理库,助力快速实现文件压缩解压功能!
· Ollama——大语言模型本地部署的极速利器
· DeepSeek如何颠覆传统软件测试?测试工程师会被淘汰吗?
· 使用C#创建一个MCP客户端