如何输入多行命令


425

是否可以将PowerShell命令行分成多行?

在Visual Basic中,我可以使用下划线(_)在下一行中继续该命令。


3
Bruce Payette的PowerShell in Action很好地涵盖了“为什么不反斜杠”问题;很棒的书。Bruce对编程语言的历史有广泛的了解。期待本书的V2。
杰伊·巴祖兹


1
抱歉,如果主题不正确,但是如果要使用sh命令提交脚本,则bash约定成立,因此可以使用反斜杠。在这种情况下,您的脚本还应该具有unix样式的结尾。
kon psych

只需使用`字符在多行上分隔命令
Asad Shakeel

Answers:


634

您可以使用带有重音符号(反勾号)的空格:

Get-ChildItem -Recurse `
  -Filter *.jpg `
  | Select LastWriteTime

但是,仅在上述情况下才需要这样做。通常,当命令在语法上无法完全完成时,您会获得自动的行连续性。这包括启动新的管道元素:

Get-ChildItem |
  Select Name,Length

可以正常工作,因为在|命令之后由于缺少另一个管道元素而无法完成。同样,打开花括号或任何其他种类的括号也可以直接继续行:

$x=1..5
$x[
  0,3
] | % {
  "Number: $_"
}

|逗号类似,在某些情况下也可以使用:

1,
2

请记住,虽然,类似于JavaScript的自动分号插入,也有一些事情,也同样打破,因为线路中断发生在那里的一个点由一个有效的声明之前:

return
  5

不管用。

最后,字符串(在所有变体中)也可能会超出一行:

'Foo
bar'

然后,它们在字符串中包括换行符。


4
另外,别忘了提及其他一些标记还充当行连续符,例如|{
基思·希尔

1
@基思:谢谢,我把它包括在内。这些可能太明显了,无法提及;-)
乔伊(Joey)2010年

16
不,最好将这些其他字符记录下来以备将来参考。
基思·希尔

1
@JackDouglas:可以在左括号直接换行,但显然不能在运算符前的表达式内。话虽如此,我认为这是对语法的疏忽。
2014年

10
显然,行连续在ISE命令窗格中不起作用。
Khouri Giordano

64

我刚刚发现,反斜线和换行符之间不能有任何字符。即使是空格也会导致该命令不起作用。


10
尽管从技术上讲这不是问题的答案,但+1是因为绝对必要。我只是很难做到这一点,并且一定会在将来的发展中尽可能避免回落。
Dave Markle 2014年

4
因此,在Powershell中,根本没有可靠的方法可以打破长线。难怪我倾向于在每个地方看到那些2屏幕宽的Powershell脚本。#ShakeMyHead
RayLuo

我也为此而苦苦挣扎...您可以在反引号之前插入一个内联注释以包含注释,例如:Some-Command`-arg1 <#说明arg 1#>`-arg2 <#说明arg 2 #>
joelsand

2
嗯 这使PowerShell代码不必要地难以发布到文档或网站中,因为担心如果使用Shift + Enter,该命令可能会被人读错,或者使用反勾号时会在ISE的命令行中解析为错误。
GuitarPicker

由于评论的性质(不完全是原始问题的完整答案),请投下反对票。
CodeBreaker

38

在大多数类似C的语言中,我故意将花括号放在我认为它们使代码最容易阅读的位置。

PowerShell的解析器识别出明显没有完成的语句,然后转到下一行。例如,想象一个带有可选脚本块参数的cmdlet:

    Get-Foo {............}

如果脚本块很长,则可能需要编写:

    Get-Foo
    {
        ......
        ......
        ......
    }

但这是行不通的:解析器将看到两个语句。第一个是Get-Foo,第二个是脚本块。相反,我写道:

    Get-Foo {
        ......
        ......
        ......
    }

我可以使用换行符(`),但这会使代码难以阅读,并引发bug。

因为这种情况要求开放括号在上一行,所以我到处都遵循这种模式:

    如果(条件){
        .....
    }

请注意,if语句需要使用语言语法中的脚本块,因此解析器将在脚本块的下一行中查找,但是为了保持一致,我将大括号放在同一行上。

同样,在长管道的情况下,我在竖线字符(|)之后中断:

    $ project.Items | 
        ?{$ _。Key -eq“ ProjectFile”} |
        %{$ _。Value} | 
        %{$ _。EvaluatedInclude} |
        %{
            ......
        }

如何做if以及foreachtry工作呢?他们允许在下一行显示脚本块...这意味着可能会发生变化
Nacht-恢复莫妮卡(Monica)2012年

@Nacht:从生锈的内存:根据语言语法,需要脚本块的语句将解析经过换行符以找到一个换行符。谁能确认?
杰伊·巴祖兹

2
@Nacht:“但这是行不通的”是指其他参数是可选的情况,在大多数情况下。
杰伊·巴祖兹

1
啊,我明白你的意思了。因此,“ if”和“ foreach”实际上不是cmdlet-它们实际上是语法的一部分,因此迫使其移至下一行。那么没有办法让用户定义的函数从下一行读取脚本块吗?我想您的上述答案正好回答了这个问题。
Nacht-恢复莫妮卡

29

扩展cristobalito的答案

我假设您是在命令行上谈论的-如果它在脚本中,则换行>充当命令定界符。

在命令行上,使用分号“;”

例如:

在命令行上签名PowerShell脚本。没有换行符。

powershell -Command "&{$cert=Get-ChildItem –Path cert:\CurrentUser\my -codeSigningCert ; Set-AuthenticodeSignature -filepath Z:\test.ps1 -Cert $cert}

10
不是问题的答案,而是您的答案回答了我的问题。:)
Frederik

1
这很有趣,但与OP要求的相反。OP希望将一条命令分成几行;您介绍了如何将多个命令合并到一行。
丹尼尔·扬科斯基

17

在PowerShell和PowerShell ISE中,还可以在每行的末尾使用Shift+ Enter进行多行编辑(而不是标准backtick `)。


2
这是编辑多行here字符串的一个很好的技巧,否则,如果您不知道该SHIFT-ENTER技巧,则很难编辑。
dpw

1
我相信只有在使用PSReadLine模块或等效模块时,PowerShell的控制台版本才会出现这种情况。在标准Windows控制台中输入功能,Enter并且Shift+Enter在功能上等效。
Bill_Stewart '17

@Bill_Stewart是的,它可以在没有PSReadline的ISE控制台中工作,但不能在控制台主机中工作。
briantist

2
需要说明的是:1)该PSReadline模块在控制台主机中工作(不适用于ISE)。2)在使用时才能Shift+Enter控制台主机中工作。3)一直在ISE工作。4)如果不使用控制台主机,在功能上等效于。PSReadlineShift+EnterPSReadlineShift+EnterEnter
Bill_Stewart '17

2
这是正确的答案,被接受并获得400票赞成的答案非常令人困惑和无用!!
FLICKER'Apr 11'18

4

如果试图将字符串分成多行,则可以使用“ +”。例如:

$header =    "Make," +

             "ComputerName," +

             "Model," +

             "Windows Version"

看起来像:

$header = "Make,ComputerName,Model,Windows Version"

2

我假设您是在命令行上谈论的-如果它在脚本中,则换行符充当命令定界符。

在命令行上,使用分号“;”


1
  1. 使用分号;分隔命令
  2. \\在任何反斜杠上替换双反斜杠\
  3. 使用"'传递安全地址转换命令,如“‘路径’”。

此ps1命令安装区域设置pfx证书。

powershell -Command "$pfxPassword = ConvertTo-SecureString -String "12345678" -Force -AsPlainText ; Import-PfxCertificate -FilePath "'C:\\Program Files\\VpnManagement\\resources\\assets\\cert\\localhost.pfx'" Cert:\\LocalMachine\\My -Password $pfxPassword ; Import-PfxCertificate -FilePath "'C:\\Program Files\\VpnManagement\\resources\\assets\\cert\\localhost.pfx'" Cert:\\LocalMachine\\Root -Password $pfxPassword"




0

只需在此处添加一个角盒即可。这样可以为您节省5分钟。如果您使用一系列动作,则需要输入“。”。在行尾,留一个空格,后跟“`”(反引号)。我发现这很困难。

$yourString = "HELLO world! POWERSHELL!". `
                  Replace("HELLO", "Hello"). `
                  Replace("POWERSHELL", "Powershell")
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.