Reputation: 6863
In this example it seems to me that the first two outputs should match, giving me formatting based on my defined culture. The last should be different because French formatting is different. Instead, the last two are the same, and are both getting some kind of default formatting. So, how do I do Culture based formatting when the time is a variable rather than formatting directly with Get-Date? It seems like it should be the same, but it's not.
get-date -format ((Get-Culture).DateTimeFormat.FullDateTimePattern)
$time = Get-Date
$pattern = 'FullDateTimePattern'
$formattedTime = $time -f (Get-Culture).DateTimeFormat.$pattern
Write-Host "$formattedTime"
$culture = New-Object system.globalization.cultureinfo('fr-FR')
$formattedTime = $time -f ($culture).DateTimeFormat.$pattern
Write-Host "$formattedTime"
The output I get is
July 9, 2019 11:22:01 AM
07/09/2019 11:22:01
07/09/2019 11:22:01
What I want to get is
July 9, 2019 11:26:46 AM
July 9, 2019 11:26:46 AM
Tuesday 9 July 2019 11:26:46
EDIT: So, based on I.T Delinquent's response, I tried this
$pattern = 'longDateTimePattern'
$date = Get-Date
$format = (Get-Culture).DateTimeFormat.$pattern
$string = ($date).ToString($format)
Write-Host $string
$culture = New-Object system.globalization.cultureinfo('de-DE')
$format = $culture.DateTimeFormat.$pattern
$string = ($date).ToString($format)
Write-Host $string
And it gave me identical results. Because it's not 'longDateTimePattern', its 'longDatePattern'. Given that the pattern could become a user supplied string, I better validate them.
Upvotes: 3
Views: 997
Reputation: 438093
Your attempt at using the -f
operator is flawed (see bottom section).
To get the desired output, use the [datetime]
type's appropriate .ToString()
overload:
$time.ToString($culture.DateTimeFormat.$pattern, $culture)
Passing $culture
as the 2nd argument ensures that the formatting is applied in the context of that culture.
If your intent is truly to use a format from another culture and apply it in the context of the current culture, simply omit the 2nd argument (as an alternative to the Get-Date -Format
approach in your question):
$time.ToString($culture.DateTimeFormat.$pattern)
If there's no need to involve a different culture, the task becomes much simpler, by way of the standard date-time format strings, where single-character strings such as "D"
refer to standard formats, such as LongDatePattern
:
$time.ToString("D")
You can also pass these strings to Get-Date -Format
Get-Date -Format D
As for what you tried:
In order for the -f
operator to work correctly, your LHS must be a string template with placeholders ({0}
for the first one, {1}
for the second, ...), to be replaced with the RHS operands.
Using a simple example:
Format the RHS, an [int], as a number with 2 decimal places.
PS> '{0:N2}' -f 1
1.00
Therefore, $time -f (Get-Culture).DateTimeFormat.$pattern
doesn't perform (explicit) formatting at all, because the LHS - $time
- contains no placeholders.
That is, the RHS is ignored, and the LHS is returned as a string: It is effectively the same as calling $time.ToString()
in the context of the invariant culture (because the result of applying the -f
operator is always a string and PowerShell uses the invariant culture in many string-related contexts).
While you can incorporate a specific date-time format string into a template-string placeholder - by following the placeholder index with :
and a format string, as shown above ({0:N2}
) - you cannot also provide a culture context for it.
You'd have to (temporarily) switch to the desired culture first:
# Save the currently effective culture and switch to the French culture
$prev = [cultureinfo]::CurrentCulture
[cultureinfo]::CurrentCulture = 'fr-FR'
# Format with the desired format string.
"{0:$($culture.DateTimeFormat.$pattern)}" -f $time
[cultureinfo]::CurrentCulture = $prev
Upvotes: 2
Reputation: 2415
I think this has something to do with how the Get-Date is passed using the variable, it seems to lose the format capability. In fact, if you try using Write-Host ($date -Format $format)
gives an error:
Unexpected token '$format' in expression or statement
Here are my setup variables:
$pattern = 'FullDateTimePattern'
$format = (Get-Culture).DateTimeFormat.$pattern
$date = Get-Date
As stated above, using Write-Host ($date -f $format)
and incorrectly outputs 07/09/2019 12:24:38
. However, using any of the below options does work and correctly outputs 09 July 2019 12:24:38
:
Write-Host (Get-Date -Format $format)
Write-Host (Get-Date).ToString($format)
Write-Host ($date).ToString($format)
Hope this helps :)
Upvotes: -1