2011-01-11 21 views
10

Al hacer algo de automatización Powershell, tengo problemas con la forma en que los datos escritos en stdout mediante un archivo .cmd se capturan automáticamente. Tengo dos funciones que hacen algo como lo siguiente:¿Cómo evito que se impriman los datos en stdout en mi valor de retorno?

function a { 
    & external.cmd # prints "foo" 
    return "bar" 
} 

function b { 
    $val = a 
    echo $val # prints "foobar", rather than just "bar" 
} 

Básicamente, los datos que external.cmd envía a la salida estándar se añade al valor de retorno de a, a pesar de que todo lo que realmente quiero volver a a es la cadena que me especificado. ¿Cómo puedo prevenir esto?

Respuesta

13

Éstos son algunos enfoques diferentes para el manejo de esto:

  • captura de la salida de la secuencia de comandos .cmd:

    $output = & external.cmd # saves foo to $output so it isn't returned from the function 
    
  • redirigir la salida a nulo (lo tiran)

    & external.cmd | Out-Null # throws stdout away 
    
  • redirigirlo a un archivo

    & external.cmd | Out-File filename.txt 
    
  • ignoran en la persona que llama por su omisión en el conjunto de objetos que se devuelve desde la función

    $val = a 
    echo $val[1] #prints second object returned from function a (foo is object 1... $val[0]) 
    

En PowerShell, se devuelve ningún valor salida de su código no captura la persona que llama (incluyendo stdout, stderr, etc.). Entonces, tiene que capturarlo o canalizarlo a algo que no devuelve un valor, o terminará con un objeto [] como su valor de retorno de la función.

La palabra clave return es realmente solo por claridad y la salida inmediata de un bloque de scripts en PowerShell. Algo como esto sería incluso trabajar (no textualmente, pero sólo para darle la idea):

function foo() 
{ 
    "a" 
    "b" 
    "c" 
} 

PS> $bar = foo 
PS> $bar.gettype() 
System.Object[] 
PS> $bar 
a 
b 
c 

function foobar() 
{ 
    "a" 
    return "b" 
    "c" 
} 

PS> $myVar = foobar 
PS> $myVar 
a 
b 
4

general, yo prefiero usar una de las siguientes dos técnicas que, en mi opinión, hacen que el código sea más legible:

  • conversión a una expresión para anular el fin de suprimir el valor de retorno:

    [void] (expression)

  • asignar la salida de Valu e para la variable $ nulo:

    $null = expression

Por ejemplo:

function foo 
{ 
    # do some work 
    return "success" 
} 

function bar 
{ 
    [void] (foo) # no output 
    $null = foo # no output 
    return "bar" 
} 

bar # outputs bar 
2

Si desea que la salida de la orden para imprimir todavía a la línea de comandos PowerShell, puede hacer una variante de la respuesta aceptada:

& external.cmd | Out-Host 
Cuestiones relacionadas