Short of using an intermediate temporary file you can use selective ^-escaping:
powershell -NoProfile -Command Get-ChildItem -Path '../' -Filter '*.doc' ^| ^
Select-Object -First 1 ^| ^
ForEach-Object { notepad "\"$($_.FullName)\"" }
Note that notepad "$_.FullName" wouldn't work in PowerShell, because you need an enclosing $(...) to reference properties inside "...". I've corrected the issue above, but note that you don't need the double quotes at all in this case.
^ must be used:
- to escape
| to prevent cmd.exe from interpreting it up front.
- Generally, you have to
^-escape all of cmd.exe's metacharacters if you want to pass them through to PowerShell: & | < > %
" instances that you want PowerShell to see literally (for them to then have syntatic meaning when interpreted as PowerShell source code) are a special case: you must \-escape them (!) and "..."-enclose the string you want to be recognized as a single argument by PowerShell, so as to preserve embedded whitespace accurately.
- to escape line endings to tell
cmd.exe that the command continues on the next line.
- Note that the
^ must be the very last character on the line.
- Also note that a line-ending
^ removes the line break, so the resulting command is a single-line command.
To include actual line breaks in your command - which are required for passing commands to a language such as Python with python -c, as eryksun points out - use ^<newline><newline>, as PetSerAl recommends:
powershell.exe -noprofile -command "\"line 1^
line 2\""
The above yields (based on PowerShell simply echoing (outputting) a quoted string literal submitted as a command):
line 1
line 2
Note: The "\" (and matching \"") is not only required to ultimately pass the string with embedded whitespace preserved correctly here, but also to present a balanced set of " on that line to cmd.exe (irrespective of \-escaping, which cmd.exe doesn't recognize) - without it, the newline-escaping ^ at the end of that line wouldn't be recognized.
PetSerAl also points out that if you're passing what PowerShell should regard a string literal, you can also pass what PowerShell ends up seeing as a single-quoted string ('...'):
powershell.exe -noprofile -command ^"'line 1^
line 2'^"
Here, the ^-escaping of the " instances are for the benefit of cmd.exe so it doesn't mistake the newline-escaping ^ as being inside a double-quoted string.