Python日期时间格式,如C#String.Format

时间:2010-11-15 19:26:35

标签: c# python datetime formatting

我正在尝试将应用程序从C#移植到Python。该应用程序允许用户使用C# String.Format DateTime formatting选择日期时间格式。 Python的日期时间格式甚至不一样,所以我不得不通过一些箍跳我的代码。

Python有没有办法解析像yyyy-MM-dd HH-mm-ss而不是%Y-%m-%d %H-%M-%S这样的字符串?

4 个答案:

答案 0 :(得分:3)

通过使用简单替换来转换格式字符串,您可以获得合适的距离。

_format_changes = (
    ('MMMM', '%B'),
    ('MMM',  '%b'), # note: the order in this list is critical
    ('MM',   '%m'),
    ('M',    '%m'), # note: no exact equivalent
    # etc etc
    )

def conv_format(s):
    for c, p in _format_changes:
        # s.replace(c, p) #### typo/braino
        s = s.replace(c, p)
    return s

我认为你的“箍”意味着类似的东西。注意有并发症:
(1)C#格式可以用单引号括起来的文字文本(你引用的链接中的例子)
(2)它可能允许通过(例如)\转义单个字符作为文字。 (3)12小时或24小时制的时钟可能需要额外的工作(我没有深入研究C#规范;这个评论是基于我参与的另一个类似的练习)。
你最终可以编写一个编译器和一个字节码解释器来绕过所有的陷阱(比如M,F,FF,FFF,......)。

另一种选择是使用ctypes或类似内容直接调用C# RTL。

更新原始代码过于简单,并且有错字/ braino。以下新代码显示了如何解决一些问题(如文字文本,并确保输入中的文字%不会使strftime不满意)。在没有直接转换(M,F等)的情况下,它不会尝试给出准确的答案。注意到可能引起例外的地方,但代码以自由放任的方式运作。

_format_changes = (
    ('yyyy', '%Y'), ('yyy', '%Y'), ('yy', '%y'),('y', '%y'),
    ('MMMM', '%B'), ('MMM', '%b'), ('MM', '%m'),('M', '%m'),
    ('dddd', '%A'), ('ddd', '%a'), ('dd', '%d'),('d', '%d'),
    ('HH', '%H'), ('H', '%H'), ('hh', '%I'), ('h', '%I'),
    ('mm', '%M'), ('m', '%M'),
    ('ss', '%S'), ('s', '%S'),
    ('tt', '%p'), ('t', '%p'),
    ('zzz', '%z'), ('zz', '%z'), ('z', '%z'),
    )

def cnv_csharp_date_fmt(in_fmt):
    ofmt = ""
    fmt = in_fmt
    while fmt:
        if fmt[0] == "'":
            # literal text enclosed in ''
            apos = fmt.find("'", 1)
            if apos == -1:
                # Input format is broken.
                apos = len(fmt)
            ofmt += fmt[1:apos].replace("%", "%%")
            fmt = fmt[apos+1:]
        elif fmt[0] == "\\":
            # One escaped literal character.
            # Note graceful behaviour when \ is the last character.
            ofmt += fmt[1:2].replace("%", "%%")
            fmt = fmt[2:]
        else:
            # This loop could be done with a regex "(yyyy)|(yyy)|etc".
            for intok, outtok in _format_changes:
                if fmt.startswith(intok):
                    ofmt += outtok
                    fmt = fmt[len(intok):]
                    break
            else:
                # Hmmmm, what does C# do here?
                # What do *you* want to do here?
                # I'll just emit one character as literal text
                # and carry on. Alternative: raise an exception.
                ofmt += fmt[0].replace("%", "%%")
                fmt = fmt[1:]
    return ofmt

测试到以下范围:

>>> from cnv_csharp_date_fmt import cnv_csharp_date_fmt as cv
>>> cv("yyyy-MM-dd hh:mm:ss")
'%Y-%m-%d %I:%M:%S'
>>> cv("3pcts %%% yyyy-MM-dd hh:mm:ss")
'3pc%p%S %%%%%% %Y-%m-%d %I:%M:%S'
>>> cv("'3pcts' %%% yyyy-MM-dd hh:mm:ss")
'3pcts %%%%%% %Y-%m-%d %I:%M:%S'
>>> cv(r"3pc\t\s %%% yyyy-MM-dd hh:mm:ss")
'3pcts %%%%%% %Y-%m-%d %I:%M:%S'
>>>

答案 1 :(得分:2)

先运行一些替换:

replacelist = [["yyyy","%Y"], ["MM","%m"]] # Etc etc
for replacer in replacelist:
    string.replace(replacer[0],replacer[1])

答案 2 :(得分:0)

我怕你不能。 strftime()调用底层C库的strftime()函数,该函数依次采用%X形式的格式化指令。 您必须编写几行代码才能进行转换。

答案 3 :(得分:0)

除了选择的答案外,它适用于所有希望使用相同格式但在c#中从python转换格式的人(将python datetime格式转换为C#可转换datetime格式),下面是一个扩展,它可以工作

public static string PythonToCSharpDateFormat(this string dateFormat)
    {
        string[][] changes = new string[][]
        {
            new string[]{"yyyy", "%Y"},new string[] {"yyy", "%Y"}, new string[]{"yy", "%y"},
            new string[]{"y", "%y"}, new string[]{"MMMM", "%B"}, new string[]{"MMM", "%b"},
            new string[]{"MM", "%m"}, new string[]{"M", "%m"}, new string[]{"dddd", "%A"},
            new string[]{"ddd", "%a"}, new string[]{"dd", "%d"}, new string[]{"d", "%d"},
            new string[]{"HH", "%H"}, new string[]{"H", "%H"}, new string[]{"hh", "%I"},
            new string[]{"h", "%I"}, new string[]{"mm", "%M"}, new string[]{"m", "%M"},
            new string[]{"ss", "%S"}, new string[]{"s", "%S"}, new string[]{"tt", "%p"},
            new string[]{"t", "%p"}, new string[]{"zzz", "%z"}, new string[]{"zz", "%z"},
            new string[]{"z", "%z"}
        };

        foreach (var change in changes)
        {
            //REPLACE PYTHON FORMAT WITH C# FORMAT
            dateFormat = dateFormat.Replace(change[1], change[0]);
        }
        return dateFormat;
    }