2

我在将日期的字符串表示形式转换为日期时间对象时遇到了困难。我的字符串是"2013424",如果我使用以下代码将字符串转换为日期时间,那么它会失败..

string format = "yyyyMd";
DateTime.TryParseExact("2013424", format, CultureInfo.InvariantCulture, DateTimeStyles.None, out dtAnswerDate);

dtAnswerDate 不包含字符串值的转换表示。

但是,如果我的字符串具有类似的值,"20130424"那么它可以正常工作。请问有什么可能的建议吗?

该值来自 Microsoft HealthVault,在我的代码中使用了 XPath 表达式。此 XPath 表达式由最终用户提供。XPath 表达式选择一个节点并使用 InnerText 属性返回值。我正在编写以下代码以供参考。

string strItemXML = healthRecordItem.GetItemXml();
XmlDocument xDoc = new XmlDocument();
xDoc.LoadXml(strItemXML);
XmlNode xpathNode = xDoc.SelectSingleNode(xpath);
When = healthRecordItem.LastUpdated != null ? healthRecordItem.LastUpdated.Timestamp : healthRecordItem.EffectiveDate;
if (xpathNode != null)
{
    return xpathNode.InnerText;
}

“strItemXML”包含以下 XML

`<thing>  
<thing-id version-stamp="a40f8c41-0329-4b0f-af56-33040a1f3ecf">de631835-c7b6-43dd-9ae9-528c26ab2204</thing-id>  
<type-id name="Appointment">4b18aeb6-5f01-444c-8c70-dbf13a2f510b</type-id>  
<thing-state>Active</thing-state>  
<flags>0</flags>  
<eff-date>2013-04-23T14:33:00Z</eff-date>  
<created>  
<timestamp>2013-02-15T12:48:42.74Z</timestamp>  
<app-id name="InstantPHR Personal Health Record">afc8707e-c160-4b7f-9856-69d5c790b1a9</app-id>  
<person-id name="Mohammed Owes">f848a184-878d-4cef-999f-dff54d2e5db2</person-id>  
<access-avenue>Online</access-avenue>  
<audit-action>Created</audit-action>  
<master-app-id>8df99894-5f36-489a-a8fd-ffe6b25b8efb</master-app-id>  
</created>  
<updated>  
<timestamp>2013-04-24T07:44:58.38Z</timestamp>  
<app-id name="InstantPHR Personal Health Record">afc8707e-c160-4b7f-9856-69d5c790b1a9</app-id>  
<person-id name="Mohammed Owes">f848a184-878d-4cef-999f-dff54d2e5db2</person-id>  
<access-avenue>Online</access-avenue>  
<audit-action>Updated</audit-action>  
<master-app-id>8df99894-5f36-489a-a8fd-ffe6b25b8efb</master-app-id>  
</updated>  
<data-xml>  
<appointment>  
<when>  
<date>  
<y>2013</y>  
<m>4</m>  
<d>24</d>  
</date>  
<time>  
<h>14</h>  
<m>33</m>  
<s>0</s>  
</time>  
</when>  
<service>  
<text>RREEESSSTTTT</text>  
</service>  
<clinic>  
<name>  
<full>Mohammed Owes</full>  
</name>  
</clinic>  
</appointment>  
<common>  
<source>InstantPHR</source>  
<extension source="phr.getrealconsulting.com.appointment_v2"/>  
</common>  
</data-xml>  
</thing>`  

并且“xpath”的值为“/thing/data-xml/appointment/when/date”。所以我的代码会返回“2013424”

4

2 回答 2

3

更新

看起来您在该 xml 中分隔了值。

您可以通过分别提取年、月和日并将其输入到DateTime接受这三个参数的构造函数中来完全避免解析:

var date = new DateTime(year, month, day);

不幸的是,我对 XPath 不太感兴趣,所以您必须自己修改那部分。


我认为这里的问题是对于月份或日期的数字可能存在歧义。我知道您用作示例的日期实际上并不模棱两可,但它仍然失败,因为潜力仍然存在。

例如:2013111。这是 11 月 1 日还是 1 月 11 日?这就是前导 0 起作用的原因,因为它可以分隔数字以消除歧义。

除非您添加空格或指定前导零,否则我认为没有办法使这种格式起作用。

空白示例:

string format = "yyyy M d";
DateTime date = DateTime.ParseExact("2013 4 24", format, CultureInfo.InvariantCulture);

您没有说明任何限制或“2013424”值的来源,因此我无法轻易建议一种解决特定于您的代码的问题的方法。

当然,如果您没有从输入点以非歧义格式捕获值,那么您在尝试理解什么是一天和什么是一个月时也会遇到这些歧义问题。

作为参考,您可以在此处找到DateTime格式字符串的文档。

于 2013-04-24T10:26:22.003 回答
1

您最好的解决方案可能是确保在尝试转换之前获得月份的两位数表示;我当然假设您正在连接原始日期的各个部分,并且它没有按2013424原样提供(这会使日期模棱两可)。

即类似的东西:

var monthString = (monthString.length > 1) ? "0" + monthString : monthString;    
var dateString = yearString + monthString + dayString;
DateTime.TryParseExact(dateString, out dtAnswerDate); 

更新:

我仍然有点不清楚为什么你不能自己获取 mont,但如果确实如此,那么基本上没有适合你的解决方案。以下是不明确日期的示例:2013111, 2013211, 2013129.

如果您不知道特定数字是一个月还是一天表示的一部分,那么您根本无法安全地解析日期。

这可能还有其他逻辑,你没有提到吗?你能想出任何方法来安全地“猜测”一个数字应该如何解释吗?或者,也许您可​​以限制或操纵用户可以以某种方式使用的 XPath 表达式?

如果没有,那么恐怕您的问题根本没有安全的解决方案。

于 2013-04-24T10:28:57.907 回答