简体   繁体   English

这个参数如何在C#中传递?

[英]How is this argument passed in C#?

I've seen this code snippet but cannot quite figure out why it can successfully run. 我已经看到了此代码段,但无法完全弄清楚为什么它可以成功运行。

class Program
{
    public static void Main()
    {
        var startInfo = new ProcessStartInfo
        {
            FileName = "PowerShell.exe",
            Arguments = @"-NoLogo -NoProfile ""Get-Content Queries.txt"" | Set-Content Output.tsv"
        };

        Console.WriteLine(startInfo.Arguments);

        Process.Start(startInfo);
    }
}

If I try to execute powershell -NoLogo -NoProfile "Get-Content Queries.txt" | Set-Content Output.tsv 如果我尝试执行powershell -NoLogo -NoProfile "Get-Content Queries.txt" | Set-Content Output.tsv powershell -NoLogo -NoProfile "Get-Content Queries.txt" | Set-Content Output.tsv directly in the command prompt it would throw error messages but the above code snippet could successfully finish. 直接在命令提示符下powershell -NoLogo -NoProfile "Get-Content Queries.txt" | Set-Content Output.tsv会引发错误消息,但是上面的代码段可以成功完成。

How are the double quotes in the code being handled? 如何处理代码中的双引号?

When you say command prompt, do you mean cmd.exe? 当您说命令提示符时,您的意思是cmd.exe吗? If so, you are dealing with cmd.exe's parsing and it isn't handling the | 如果是这样,则说明您正在处理cmd.exe的解析,并且无法处理| very well eg: 很好,例如:

C:\>dir | foo.txt
'foo.txt' is not recognized as an internal or external command,
operable program or batch file.

If I try your command from a PowerShell V4 prompt, it works fine. 如果我在PowerShell V4提示符下尝试您的命令,则可以正常工作。 Also, the script executed in C# is using PowerShell's command line parsing and not cmd.exe's parsing. 另外,在C#中执行的脚本使用PowerShell的命令行解析而不是cmd.exe的解析。

Command line parameters are parsed using spaces as a delimiter which can be of course be a problem for things such as paths which have spaces eg Get-Content Queries.txt . 命令行参数使用空格作为定界符进行解析,这对于诸如路径之类的带有空格的东西(例如Get-Content Queries.txt当然是个问题。 So to get around this, any parameters enclosed in double quotes will avoid this type of parsing-by-space-delimiter. 因此,为了解决这个问题,用双引号引起来的任何参数都将避免这种类型的按空格分隔符进行解析。

So why do the double quotes work? 那么为什么双引号有效呢?

With the code in question, because the string is prefixed with the @ string literal, the double quotes are allowed without escaping. 对于有问题的代码,因为字符串以@字符串文字作为前缀,所以允许双引号而不进行转义。 A nice short post on how the @ string literal modifier works (by Jon Skeet no less) can be found at What does an @ before the start of a string literal mean? 有关@字符串文字修饰符如何工作的简短文章(乔恩·斯凯特(Jon Skeet)同样如此)可以在以下位置找到: @在字符串文字开始之前是什么意思? . To quote a sentence from that: 引用一句话:

It basically means, "don't apply any interpretations to characters until the next quote character is reached". 它的基本含义是:“直到到达下一个引号字符时,才对字符进行任何解释”。 So, a verbatim string literal can contain backslashes (without them being doubled-up) and even line separators. 因此,逐字字符串文字可以包含反斜杠(不加倍),甚至可以包含行分隔符。 To get a double-quote (") within a verbatim literal, you need to just double it... 要在逐字文字中获得双引号(“),只需将其加倍...

But copying to the command-line manually doesn't work, what's different? 但是手动复制到命令行不起作用,有什么不同?

So when copying this to the command-line, this won't work in exactly the same way because it doesn't include the extra step that Process.Start() takes in wrapping the arguments in (wait for it...) another quote! 因此,在将其复制到命令行时,它不会以完全相同的方式工作,因为它不包括Process.Start()将参数包装在另一个(等待它)中的额外步骤。引用! As described in PowerShell and double quotes on the command line : PowerShell和命令行中的双引号所述

Here's some ways to make this work properly: 以下是一些可以使其正常工作的方法:

  • Use single quotes: 使用单引号:

    powershell.exe C:\\Scripts\\ParamCheck.ps1 -Something 'one two'

  • Use a backslash delimiter (even though PowerShell internally uses the left-single-quote `): 使用反斜杠分隔符(即使PowerShell内部使用左单引号`):

    powershell.exe C:\\Scripts\\ParamCheck.ps1 -Something \\"one two\\"

  • Use three double quotes: 使用三个双引号:

    powershell.exe C:\\Scripts\\ParamCheck.ps1 -Something """one two"""

References: 参考文献:

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

相关问题 如何在C#中为传递给Thread的参数转换数据类型 - How can I convert datatype for argument passed into Thread in C# 作为参数传递给onclick()的C#变量未定义 - C# variable passed as argument to onclick() is undefined 如何在C#中传递“this” - How is “this” passed in C# 参数从C#代码错误地传递到C ++ DLL - Argument passed incorrectly from C# code to C++ DLL 如何处理作为参数传递给方法的Lambda表达式 - C#.NET 3.5 - How to Process Lambda Expressions Passed as Argument Into Method - C# .NET 3.5 C#泛型如何获取没有对象类型作为参数的泛型方法的参数类型? - C# Generics How Can I get the type passed as an argument for a generic method with no object type as a parameter? 当委托作为通用参数传递时调用C#委托方法 - Invoking C# Delegate Method when delegate is passed as Generic Argument C# 如果数组是通过引用传递的,为什么必须使用修饰符 ref 传递参数数组? - C# Why does the argument array has to be passed with the modifier ref if arrays are passed by reference? 如何在 C# 中检查日期是否已经过去? - How to check if a date has passed in C#? c#中参数是如何传递给URL的? - How are parameters passed to URL in c#?
 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM