简体   繁体   English

运行带有变量 -Path 参数的 Powershell 命令

[英]Running a Powershell command with a variable -Path parameter

Can someone please explain the following behaviour to me?有人可以向我解释以下行为吗?

PS C:\Users\Kenny> $filePath = "C:\\Complicated.File.Path.That.Has.Special-Chars`[but-no.spaces`]and.definitely.exists\"
PS C:\Users\Kenny> cd $filePath
cd : Cannot find path 'C:\\Complicated.File.Path.That.Has.Special-Chars[but-no.spaces]and.definitely.exists\' because it does not exist.
At line:1 char:1
+ cd $filePath
+ ~~~~~~~~~~~~~~~~                                 
    + CategoryInfo          : ObjectNotFound: (C:\\Complicated...initely.exists\:String) [Set-Location], ItemNotFoundE
   xception
    + FullyQualifiedErrorId : PathNotFound,Microsoft.PowerShell.Commands.SetLocationCommand

PS C:\Users\Kenny> cd 'C:\\Complicated.File.Path.That.Has.Special-Chars`[but-no.spaces`]and.definitely.exists\'
PS C:\Complicated.File.Path.That.Has.Special-Chars[but-no.spaces]and.definitely.exists> cd c:
PS C:\Users\Kenny> Write-Host $filePath
C:\\Complicated.File.Path.That.Has.Special-Chars[but-no.spaces]and.definitely.exists\
PS C:\Users\Kenny> cd "$filePath"
cd : Cannot find path 'C:\\Complicated.File.Path.That.Has.Special-Chars[but-no.spaces]and.definitely.exists\' because it does not exist.
At line:1 char:1
+ cd "$filePath"
+ ~~~~~~~~~~~~~~~~~~
    + CategoryInfo          : ObjectNotFound: (C:\\Complicated...initely.exists\:String) [Set-Location], ItemNotFoundE
   xception
    + FullyQualifiedErrorId : PathNotFound,Microsoft.PowerShell.Commands.SetLocationCommand

PS C:\Users\Kenny> cd ${filePath}
cd : Cannot find path 'C:\\Complicated.File.Path.That.Has.Special-Chars[but-no.spaces]and.definitely.exists\' because it does not exist.
At line:1 char:1
+ cd ${originalPath}
+ ~~~~~~~~~~~~~~~~~~
    + CategoryInfo          : ObjectNotFound: (C:\\Complicated...initely.exists\:String) [Set-Location], ItemNotFoundE
   xception
    + FullyQualifiedErrorId : PathNotFound,Microsoft.PowerShell.Commands.SetLocationCommand

PS C:\Users\Kenny> cd ${$filePath}
cd : Cannot process argument because the value of argument "path" is null. Change the value of argument "path" to a
non-null value.
At line:1 char:1
+ cd ${$filePath}
+ ~~~~~~~~~~~~~~~~~~~
    + CategoryInfo          : InvalidArgument: (:) [Set-Location], PSArgumentNullException
    + FullyQualifiedErrorId : ArgumentNull,Microsoft.PowerShell.Commands.SetLocationCommand

PS C:\Users\Kenny> cd $($filePath)
cd : Cannot find path 'C:\\Complicated.File.Path.That.Has.Special-Chars[but-no.spaces]and.definitely.exists\' because it does not exist.
At line:1 char:1
+ cd $($filePath)
+ ~~~~~~~~~~~~~~~~~~~
    + CategoryInfo          : ObjectNotFound: (C:\\Complicated...initely.exists\:String) [Set-Location], ItemNotFoundE
   xception
    + FullyQualifiedErrorId : PathNotFound,Microsoft.PowerShell.Commands.SetLocationCommand

If I had a penny for every minute I've wasted on PowerShell's insistance that backticks, quotes and other meta-characters are just right , I would be the richest man on Earth!如果我在 PowerShell 坚持认为反引号、引号和其他元字符正确无误上浪费的每一分钟都有一分钱,那么我将成为地球上最富有的人! Somebody please save me from this madness!有人请救我脱离这种疯狂!

And BTW, what I'm actually trying to do is recurse through a bunch of folders and delete everything that isn't a video file, like so...顺便说一句,我实际上想要做的是通过一堆文件夹递归并删除不是视频文件的所有内容,就像这样......

Remove-Item -Path $filePath -Recurse -Exclude '*.avi','*.mkv','*.mp4'

...which doesn't work for (presumably) the same reason: not being able to pass a variable to the -Path parameter. ...这对于(可能)同样的原因不起作用:无法将变量传递给-Path参数。 And if someone is feeling really generous, they could also help me with this .如果有人真的很慷慨,他们也可以帮助 MTIA: :D MTIA: :D

Use -LiteralPath instead of -Path because some of the special characters where interpreted with -Path .使用-LiteralPath而不是-Path因为某些特殊字符是用-Path解释的。

Remove-Item -LiteralPath

Special characters are just so much fun in PS right?特殊角色在 PS 中真的很有趣,对吧?

-LiteralPath works exactly like Patrick explained, but they don't allow for wildcards; -LiteralPath 的工作方式与 Patrick 解释的完全一样,但它们不允许使用通配符; because they're literal.因为它们是字面的。

Have you tried using single quotes ' instead of double quotes ". This allows you to escape special characters, while still evaluating wildcards. Try the commands below:您是否尝试过使用单引号 ' 而不是双引号 "。这允许您转义特殊字符,同时仍然评估通配符。请尝试以下命令:

New-Item -Path 'C:\Users\username\PSScripts\bracket`[\te$t.txt'
Get-Item -Path  'C:\Users\username\PSScripts\bracket`[\*'

Also, if it helps, I use VSCode for most scripting and, if you use tab completion, it will format this properly for you.此外,如果它有帮助,我将 VSCode 用于大多数脚本,如果您使用制表符完成,它会为您正确格式化。

I hope that helps!我希望这会有所帮助!

The solution to my overall problem ended up being this line of my batch script:我的整体问题的解决方案最终是我的批处理脚本的这一行:

powershell -Command "Get-ChildItem -Recurse -LiteralPath %filePath% | Where-Object Extension -match '^(?!(\.avi|\.mkv|\.mp4)$)' | Remove-Item"

The regex was the hardest to get right, since I haven't used negative lookaheads before, but after ~2 hours of total time spent on this one line of code , it finally works!正则表达式是最难正确的,因为我之前没有使用过负前瞻,但是在这行代码上花费了大约 2 小时的总时间后,它终于可以工作了!

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM