.netcalendarcultureinfoiformatproviderdatetimeformatinfo

When using DateTimeFormatInfo, Which Culture is used in generating the result string?


When I use DateTimeFormatInfo, Sometimes current thread culture is used for generating the result string and some times the culture I get DateTimeFormatInfo from it. Also there is situation where Invariant Culture is used. What is the logic behind it?


Solution

  • When we build a DateTimeFormatInfo, it always specify the format string. If we pass it as IFormatProvider to the ToString or string.Format methods, its calendar used for displaying datetime too (date elements calculated by that calendar) but if we do not pass it, current culture info passed as IFormatProvider by default and so current culture calendar used for calculation of date time elements. In Four special case, despite every culture you used for creating DateTimeFormatInfo or every IFormatProvider you pass to those methods, Invariant Culture and Invariant Calendar used. These are: "O" (or "o"), "R" (or "r"), "s", and "u". The following example show some example:

     static void ChangeStandardFormatStringAssociation()
        {
            // Build a writable instance of DateTimeFormatInfo which is get from writable CultureInfo (for example using ctor or using CreateSpecificCulture)
            var formatInfo = CultureInfo.CreateSpecificCulture("en-US").DateTimeFormat; // d standard format associated by "MM-dd-yyyy" in short Date for en-US but we want to change it to "dd-MM-yyyy"
            Console.WriteLine($"Culture which FormatInfo built from:en-US (This can not calculate from FormatInfo)");
            Console.WriteLine($"FormatInfo is readonly?{formatInfo.IsReadOnly}");
            Console.WriteLine(formatInfo.ShortDatePattern);
            CultureInfo.CurrentCulture = new CultureInfo("fa-IR");
            // What is current culture?
            Console.WriteLine($"Current Culture is :{Thread.CurrentThread.CurrentCulture.Name}");
            var dt = DateTime.Now.ToUniversalTime();
            Console.WriteLine($"{dt:d} (Current Culture)");// consider that if we do not specify formatInfo it uses the current culture 
            Console.WriteLine($"{dt.ToString("d", formatInfo)} (Culture which formatInfo built from)"); // It uses Calendar related to that cultureInfo and then calculate parts of given date in that culture and shows them
            Console.WriteLine($"{dt.ToString(formatInfo.ShortDatePattern)} (Culture which formatinfo build from Get the format string and calendar properties from current culture is used)");
            Console.WriteLine($"{dt.ToString("r", CultureInfo.CurrentCulture)} (Invariant Culture and Invariant Calendar used Even we pass other culture info)");
            Console.WriteLine($"{dt.ToString(formatInfo.ShortDatePattern, formatInfo)} (Culture which formatinfo build from Get the format string and calendar properties from that culture is also used since we set it as format provider)");
    
        }