Thursday, October 29, 2009

Using F# BigInt in PowerShell

Occasionally I have the need to utilize large precise numbers within PowerShell. Unfortunately, the native data types that we can use are limited in their precision.
  • Float: 7 digits
  • Double: 16 digits
  • Decimal: 29 digits

I have been researching F# and came across a data type called BigInt. I now knew that I could go back to PowerShell and take advantage of this type.

The process to do so is straight forward:
First add a reference to the FSharp.Core assembly

Add-Type -Path 'C:\Program Files (x86)\FSharp-1.9.6.16\bin\fSharp.Core.dll'

Now you do things like:
PS C:> [Microsoft.FSharp.Math.BigInt]::Pow(17,71).toString()
PS C:>2300771122759378216336589429524308
0278517973481542540644504860767306
72752491528319986033

So if you are a fan of http://projecteuler.net/ you now have another tool you can utilize.

Enjoy!

Friday, October 2, 2009

Defining Object Formatting or "How to always show Military time"

A former colleague of mine at the OSU Medical Center recently asked a PowerShell related question.

Wait - Stop - Let's start over. I must digress a moment, please be patient as I give this former colleague of mine an appropriate introduction.

This Buckeye transplant to the state of Texas is much more then a former workmate, his legacy persists in innumerable ways. I won't take your time listing many of them, but I do have to share at least one. Notice the name of my blog? It isn't named after a South Park character, nor is it named after some pirate fetish. No this transplanted Buckeye is the source of FatBeard. He has a peculiar ability to derive nicknames that persist way beyond any code or script he has ever written. I fell prey to his moniker making over 3 years ago.

OK - now that you know how FatBeard came to be, lets move on with the PowerShell related post.

Texas asked me the following:
When I type Get-ChildItem (dir, ls) and get a file listing I want to see the LastWriteTime in Military format. Easy enough! I sent him this:

Get-ChildItem | select @{Name="LWT";Expression={"{0:d} {0:HH}:{0:mm}" -f ($_.LastWriteTime)}}

His response went something like this (paraphrased for the children in the audience) . "You obtuse gluteus maximus, why would I want to type that each and every time I need a directory listing." Admittedly, he had a point.

Thus begins my first foray into extending types. Using this as my guide (http://msdn.microsoft.com/en-us/library/ms714665(VS.85).aspx), I was able to quickly accomplish the task.

My steps were as follows:

  1. Navigate to C:\Windows\System32\WindowsPowerShell\v1.0 and make a copy of FileSystem.format.ps1xml
  2. Rename the copied file (CustomFileSystem.format.ps1xml)
  3. Open the renamed file and look for the tag.
  4. You should find something like this -
    [String]::Format("{0,10} {1,8}", $_.LastWriteTime.ToString("d"), $_.LastWriteTime.ToString("t"))
  5. As you can see, this handles the LastWriteTime formating for FileSystem related information. All we need to do is change it to meet our need. This should do -
  6. [String]::Format("{0,10} {1,2}:{2,2}:{3,2}", $_.LastWriteTime.ToString("d"),
    $_.LastWriteTime.ToString("HH"), $_.LastWriteTime.ToString("mm"),
    $_.LastWriteTime.ToString("ss"))
  7. Save the file.
  8. We now need to load the new formatting. Easy enough!
    Update-FormatData -prependPath 'C:\WINDOWS\system32\windowspowershell\v1.0\ CustomFileSystem.format.ps1xml'
  9. Verify your custom formatting by typing a few Get-ChildItem commands.
Now that wasn't to hard was it! Well Texas is happy now and you know how to modify object formatting (and how FatBeard came to be).

Enjoy!