不指定格式的自动日期/时间分析器



我正在搜索一个java库,它可以在不指定格式的情况下将字符串解析为POJO。我研究过POjava。还有其他图书馆做类似的事情吗?

DateTime dateTime = DateTimeParser.parse("21/02/13");
//If unclear use the cultural information passed
DateTime dateTime = DateTimeParser.parse("01/02/13", new Locale("en-us"));
//Should also work with time zones
DateTime dateTime = DateTimeParser.parse("2011/12/13T14:15:16+01:00");

我发现以下链接也有同样的问题——Java的智能日期/时间解析器,但不是很有用的答案。Joda和JCchronic都没有做我想做的事。如果我错了,请纠正我。

更新:

我说Joda不能解决我的目的的原因是,Joda希望字符串以ISO8601格式或您指定的任何格式(如"yyyyMMdd")进行解析。我将无法对这种格式进行硬编码,因为我需要处理几种格式。

我有一个破解解决方案,可以消除美国或欧洲日期格式的歧义,即mm/dd/yy或dd/mm/yy。假设我可以访问日期的时区,我能确定它是美国格式还是欧洲格式吗?有人能告诉我怎么做吗?在谷歌上搜索,但一无所获。

问题是有些格式无法猜对。

一个简单的例子是01/02/2013。这是二月一号还是一月二号?甚至更糟:01/02/09

这两种格式都存在。(谢谢,英国和美国!)

因此,任何格式的猜测者都必须依靠运气才能获得这些格式,或者故意失败。

python模块dateutil.parser可以作为尽力而为解析器的一个例子。很抱歉,我不知道java的等价物。但你可能想看看Joda Time

http://labix.org/python-dateutil#head-b95ce2094d189a89f80f5ae52a05b4ab7b41af47

它实际上具有参数CCD_ 4和CCD_。

然后是一个perl模块:

https://metacpan.org/pod/Time::ParseDate

您可能可以使用该模块的优先级列表。盲目尝试多种模式不是很快(优化的lexer会更快),但它可能对你来说已经足够好了,除非你在猜测数百万条记录的格式。

我找到了问题的答案。我使用了这个特殊的库POjava。本页介绍如何在不指定任何格式的情况下设置日期+时间字符串的格式。然而,为了使库正常工作,您必须指定日期顺序,如Day后跟Month或Month后跟Day。

对此没有神奇的解决方案。请记住,日期/时间格式也可能取决于您的区域设置。

实际上,你能做的最好的事情就是定义一个格式列表,然后一个接一个地"尝试"它们,直到你找到一个(或没有)合适的。

private static final FORMAT_1 = "MM/dd/yyyy'T'HH:mm:ss.SSS"
private static final FORMAT_2 = "MM/dd/yyyy'T'HH:mm:ss"
private static final FORMAT_3 = "MM/dd/yyyy"

在java中使用日期/时间对象时,请记住要考虑线程安全性。我有一个类在做这类事情,名为"ThreadSafeDateTimeFormatter"。

祝你好运!

由于我没有找到方便的解决方案,我写了一个简单的静态实用程序方法来帮助我。如果添加更多的格式,将格式封装在集合中并对其进行迭代可以使事情变得更容易。

public static Date returnDateFromDateString(String propValue) throws Exception {
    SimpleDateFormat sdfFormat1 = new SimpleDateFormat(IDateFConstants.DATE_STRING_FORMAT_1);
    SimpleDateFormat sdfFormat2 = new SimpleDateFormat(IDateFConstants.DATE_STRING_FORMAT_2);
    SimpleDateFormat sdfISO8601 = new SimpleDateFormat(IDateFConstants.DATE_STRING_ISO_8601);
    try {
        return sdfFormat1.parse(propValue);
    } catch (ParseException e) { }
    try {
        return sdfFormat2.parse(propValue);
    } catch (ParseException e) { }
    try {
        return sdfISO8601.parse(propValue);
    } catch (ParseException e) { }
    throw new Exception(IDateFConstants.DATE_FORMAT_ERROR);
}

其中IDateFConstants看起来像

public interface IDateFConstants {
public static final String DATE_STRING_ISO_8601 = "yyyy-MM-dd'T'HH:mm:ss";
public static final String DATE_STRING_FORMAT_1 = "dd.MM.yyyy";
public static final String DATE_STRING_FORMAT_2 = "dd.MM.yyyy HH:mm:ss";
public static final String DATE_FORMAT_ERROR = "Date string wasn't" + 
                                            + "formatted in known formats";
}

您至少需要有一个有序的候选模式列表。一旦你有了它,ApacheDateUtils就有了一个parseDate(String dateString, String[] patterns)方法,让你可以轻松地在日期字符串上尝试一个模式列表,并通过第一个匹配的模式进行解析:

public static Date parseDate(String str,
                         String[] parsePatterns)
                  throws ParseException
Parses a string representing a date by trying a variety of different parsers.

解析将依次尝试每个解析模式。解析仅被视为如果它解析了整个输入字符串,则会成功。如果没有解析模式匹配,则抛出ParseException。

解析程序将对解析的日期宽容一些。

        public static String detectDateFormat(String inputDate, String requiredFormat) {
        String tempDate = inputDate.replace("/", "").replace("-", "").replace(" ", "");
        String dateFormat;
        if (tempDate.matches("([0-12]{2})([0-31]{2})([0-9]{4})")) {
            dateFormat = "MMddyyyy";
        } else if (tempDate.matches("([0-31]{2})([0-12]{2})([0-9]{4})")) {
            dateFormat = "ddMMyyyy";
        } else if (tempDate.matches("([0-9]{4})([0-12]{2})([0-31]{2})")) {
            dateFormat = "yyyyMMdd";
        } else if (tempDate.matches("([0-9]{4})([0-31]{2})([0-12]{2})")) {
            dateFormat = "yyyyddMM";
        } else if (tempDate.matches("([0-31]{2})([a-z]{3})([0-9]{4})")) {
            dateFormat = "ddMMMyyyy";
        } else if (tempDate.matches("([a-z]{3})([0-31]{2})([0-9]{4})")) {
            dateFormat = "MMMddyyyy";
        } else if (tempDate.matches("([0-9]{4})([a-z]{3})([0-31]{2})")) {
            dateFormat = "yyyyMMMdd";
        } else if (tempDate.matches("([0-9]{4})([0-31]{2})([a-z]{3})")) {
            dateFormat = "yyyyddMMM";
        } else {
//add your required regex
            return "";
        }
        try {
            String formattedDate = new SimpleDateFormat(requiredFormat, Locale.ENGLISH).format(new SimpleDateFormat(dateFormat).parse(tempDate));
            return formattedDate;
        } catch (Exception e) {
            return "";
        }
    }

此日期/时间分析器支持20多种日期格式,用户可以将日期格式设置为输入配置。查看完整的文档,它比其他日期时间库做得更多。

Github链接:https://github.com/zoho/hawking.由ZOHO ZIA团队提供。

Hawking Parser是一个基于Java的NLP解析器,用于解析日期和时间信息。最流行的解析器,如Heidel Time、SuTime和Natty Date时间解析器,都是基于规则的。因此,他们往往难以解析日期/时间信息,需要考虑上下文、时态、多个值等更复杂的因素。

考虑到这一点,Hawking Parser旨在解决许多这些挑战,并且与其他可用的日期/时间解析器相比具有许多明显的优势。

它是GPLv3下的一个开源库,也是最好的一个。要知道为什么它是最好的,请查看这个博客,详细解释:https://www.zoho.com/blog/general/zias-nlp-based-hawking-date-time-parser-is-now-open-source.html

第页。S: 我是这个项目的开发人员之一

相关内容

  • 没有找到相关文章

最新更新