Translating from cmd.exe to PowerShell: dir

After a long hiatus from Monad, err, PowerShell, I have started working with it again now that Release Candidate 1 is available.

One thing that frustrated me when I last used the shell was figuring out how to do all the things I was used to doing with dir in cmd.exe. Things like dir /o:d to order by date, or dir /a:r to show me all the read-only files seemed to take a huge amount of typing in Monad.

It can still take a bit of typing in PowerShell but last night I decided to make a little table that translated common actions in cmd.exe’s dir to PowerShell’s get-childitem. There are two lines for each entry in the table. One is the “full” version without use of parameter shortening or use of built-in aliases, and the second is the shortest I could make the command using the aliases that ship with PowerShell. My one concession: even in the full version I never use get-childitem. I always use “dir.”

cmd.exe PowerShell
dir dir
dir /s dir -recurse
  dir -r
dir /s *.txt dir -recurse -include *.txt
  dir -r -i *.txt
dir /s %temp%\*.txt   dir -recurse -include *.txt $env:temp
  dir -r -i *.txt $env:temp
dir /o:-d dir | sort-object -descending {$_.LastWriteTime}
  dir | sort -des LastWriteTime
dir /a:d dir | where-object {$_.PSIsContainer}
  dir | ? {$_.PSIsContainer}
dir /a:-d dir | where-object {$_.PSIsContainer}
  dir | ? {!$_.PSIsContainer}
dir /a:d /o:-d dir | where-object {$_.PSIsContainer} | sort -descending {$_.LastWriteTime}
  dir | ? {$_.PSIsContainer} | sort -des LastWriteTime
dir /a:hd dir -force | where-object {$_.Attributes -like ‘*Hidden*’ -and $_.PSIsContainer}
  dir -fo | ? {$_.Attributes -like ‘*H*’ -and $_.PSIsContainer}
dir /b dir | format-table Name -hideTableHeaders
  dir | ft Name -h

 

One nice thing about functions in PowerShell: / and – are legal in function names. So, in my profile, I’ve defined functions with names like dir/o-d and dir/s to get back to the short commands I’m used to.

Coming soon: a list of things you can do with get-childitem in PowerShell that aren’t possible with dir in cmd.exe.

Tags: , , ,

7 Comments

  1. DBMwS says:

    For dir /a:hd, although I liked your approach on displaying hidden files, there is another solution that i have come up with(well it’s been around to be honest) and it’s a bit longer

    My solution would basically check the “flag” of attribute instead of comparing the string.

    Longest version:
    ls -Force | ? { ($_.attributes -band [System.IO.FileAttributes]“Hidden”) -eq [System.IO.FileAttributes]“Hidden” }

    You can leave out “System” and it becomes
    Shorter version:
    ls -Force | ? { ($_.attributes -band [IO.FileAttributes]“Hidden”) -eq [IO.FileAttributes]“Hidden” }

    Now, there is no need to check if value of “($_.attributes -band [IO.FileAttributes]“Hidden”)” is equal to the value of ‘[IO.FileAttributes]“Hidden”‘ at all, so
    Even Shorter version:
    ls -Force | ? { ($_.attributes -band [IO.FileAttributes]“Hidden”) }

    Well, you can’t leave out “[IO.FileAttributes]” type there because without casting “HIdden”, to FileAttributes, PowerShell would consider “Hidden” as string

    Btw, you can actually substitute ‘-band [IO.FileAttributes]“Hidden”‘ with “-band 2″ since the enum value of Hidden is 2.

    The SHORTEST version:
    # but not recommended for readability issue IMHO
    ls -fo | ? { ($_.attributes -band 2) }

  2. DBMwS says:

    Woops.
    Sorry about reposting. I have forgotten to include filter for directory. So would you moderate my previous post to include “-and $_.PsIsContainer”?
    Here is the revised version
    ls -fo | ? { ($_.attributes -band 2) -and $_.PsIsContainer}

  3. Thanks for the pointer to using IO.FileAttributes and, in particular, the use of the binary-and comparison operator. I’m going to spend some time reading through your blog, too — looks like you have some good info there.

  4. DBMwS says:

    NP, there Tommy, I just wanted to point out that there are many ways(too many possibly ? ;)) to do the same thing.

    It’s just amazing how much you can do with just one line with PowerShell… ;)

  5. Harri says:

    Also dot (.) seems to work in function name – so you can define: function cd..{set-location ..} in profile.

  6. trix says:

    Im a powershell newbie and this took me ages so i would be greatfull if anyone knows of a better way. I essentailly wanted the powershell dir to behave like the cmd.exe dir and put directories at the top. this is what i ended up with:

    $results = Get-ChildItem | where-Object { $_.PSIsContainer -eq 1 }
    $results2 = Get-ChildItem | Where-Object { $_.PSIsContainer -eq 0 }
    $results+$results2

    with
    remove-item alias:\dir
    set-alias dir C:\\Cmd-Dir.ps1
    in my profile

    is there a simpler way!?

    thanks

  7. I just have to say thank you for this information. Most books and material just focus on object access and stuff, but not much in the way of practical material do do real world shell stuff.

    This material helps.