我收到一个日期值如下的JSON对象:
{"PostingDate":"\/Date(1325134800000-0500)\/"}
我想用Java代码将其解析为Date
或将其作为String
。
我想知道这样做的简单方法。
答案 0 :(得分:5)
我认为第一个数字(1325134800000
)是自纪元以来的毫秒数,-0500
是时区。考虑到下面的示例代码,这似乎就是这种情况,这似乎可以满足您的需求。
以下代码使用Jackson解析JSON输入,如果您还没有选择的JSON解析库,我建议您这样做。它缺乏错误检查等。
示例代码:
public final class Foo
{
public static void main(final String... args)
throws IOException
{
// What the JSON value must match exactly
// Not anchored since it will be used with the (misnamed) .matches() method
final Pattern pattern
= Pattern.compile("\\\\/Date\\((\\d+)(-\\d+)?\\)\\\\/");
final ObjectMapper mapper = new ObjectMapper();
// Parse JSON...
final JsonNode node = mapper.readTree(
"{\"PostingDate\": \"\\/Date(1325134800000-0500)\\/\"}");
if (!node.has("PostingDate")) {
System.err.println("Bad JSON input!");
System.exit(1);
}
// Get relevant field
final String dateSpec = node.get("PostingDate").getTextValue();
// Try and match the input.
final Matcher matcher = pattern.matcher(dateSpec);
if (!matcher.matches()) {
System.err.println("Bad pattern!"); // Yuck
System.exit(1);
}
// The first group capture the milliseconds, the second one the time zone
final long millis = Long.parseLong(matcher.group(1));
String tz = matcher.group(2);
if (tz.isEmpty()) // It can happen, in which case the default is assumed to be...
tz = "+0000";
// Instantiate a date object...
final Date date = new Date(millis);
// And print it using an appropriate date format
System.out.printf("Date: %s %s\n",
new SimpleDateFormat("yyyy/MM/dd HH:MM:ss").format(date), tz);
}
}
输出:
Date: 2011/12/29 06:12:00 -0500
答案 1 :(得分:0)
Hier是一种基于fge版本的工作解析方法,但改进为
=>
private static final Pattern bingTimePattern = Pattern.compile("\\/Date\\((\\d+)([-+]\\d+)?\\)\\/");
public static DateTime parseBingTime(String timeAsString) throws ParseException {
Matcher matcher = bingTimePattern.matcher(timeAsString);
if (!matcher.find())
throw new ParseException("wrong date time format " + timeAsString, 0);
final long millis = Long.parseLong(matcher.group(1));
String tz = matcher.group(2);
if (tz.isEmpty())
tz = "+0000";
return new DateTime(millis, DateTimeZone.forID(tz));
}
答案 2 :(得分:0)
我使用Jquery DatePicker创建了一个简单的JavaScript函数
function JsonToJSDate(jsonDate) { var reg = /-?\d+/; var m = reg.exec(jsonDate); return new Date(parseInt(m[0])); }
$('#Started')。val($。datepicker.formatDate('mm / dd / yy',JsonToJSDate(yourDateVarHere)));
答案 3 :(得分:0)
简单的事情,但处理我的工作。 从JSON中提取对象值并应用子字符串 e.g:
String postingDateObjectValue = "\\/Date(1442436473422)\\/";
String dateStringInMillis = postingDateObjectValue .substring(7,20);
现在解析millis并在任何你想要的地方使用它们。
答案 4 :(得分:0)
在Java> = 8中,您可以使用new java.time
API。
输入包含:
1325134800000
),这是自unix纪元以来的毫秒数(1970-01-01T00:00Z
)-0500
),这是与UTC的区别(在这种情况下,比UTC晚了5个小时)在新的java.time
API中,有lots of different types个日期/时间对象。在这种情况下,我们可以选择使用java.time.Instant
(表示自unix epoch以来的纳秒数)或java.time.OffsetDateTime
(表示转换为日期/时间的Instant
具体抵消)。
要解析String
,我使用java.time.format.DateTimeFormatterBuilder
创建java.time.format.DateTimeFormatter
。我还使用java.time.temporal.ChronoField
来指定我正在解析的字段:
DateTimeFormatter fmt = new DateTimeFormatterBuilder()
// epoch seconds
.appendValue(ChronoField.INSTANT_SECONDS)
// milliseconds
.appendValue(ChronoField.MILLI_OF_SECOND, 3)
// offset
.appendPattern("xx")
// create formatter
.toFormatter();
我还使用正则表达式从输入String
中提取相关部分(尽管您也可以使用substring()
来获取它):
String s = "/Date(1325134800000-0500)/";
// get just the "1325134800000-0500" part - you can also do s.substring(6, 24)
s = s.replaceAll(".*/Date\\(([\\d\\+\\-]+)\\)/.*", "$1");
然后我可以解析我想要的类型:
// parse to Instant
Instant instant = Instant.from(fmt.parse(s));
// parse to OffsetDateTime
OffsetDateTime odt = OffsetDateTime.parse(s, fmt);
Instant
相当于2011-12-29T05:00:00Z
(Instant
只是时间轴中的一个点,您可以认为它总是以UTC为单位)。
OffsetDateTime
具有相同的时刻,但转换为-0500
偏移量,因此其值为2011-12-29T00:00-05:00
。但Instant
和OffsetDateTime
代表了相同的时间点。
要转换为java.util.Date
,请使用Instant
:
// convert to java.util.Date
Date date = Date.from(instant);
// if you have an OffsetDateTime, you can do this:
Date date = Date.from(odt.toInstant());
那是因为java.util.Date
has no timezone/offset information并且它只代表自unix时代以来的毫秒数(Instant
的相同概念),所以它可以很容易地从{{1 }}
对于Java 6和7,您可以使用ThreeTen Backport,这是Java 8的新日期/时间类的一个很好的后端。对于 Android ,您还需要ThreeTenABP(更多关于如何使用它here)。
与Java 8的不同之处在于包名称(在Java 8中为Instant
而在ThreeTen Backport(或Android的ThreeTenABP中)为java.time
),但类和方法名称强>是一样的。因此,org.threeten.bp
和Instant
的格式化程序创建和解析代码是相同的。
另一个区别是,在Java< = 7中,OffsetDateTime
类没有java.util.Date
方法。但您可以使用from()
类进行转换:
org.threeten.bp.DateTimeUtils