我有一个VB6应用程序,可以在SQL Server中使用日期时间值(显然将日期存储为mm / dd / yyyy)。
我需要以dd / mm / yyyy的形式向用户表示这些日期,以dd / mm / yyyy的形式读取它们,然后将它们作为标准mm / dd / yyyy存储回数据库。
这是我当前的代码片段,其中拉动+插入日期,但是我已经阅读了许多处理转换的冲突方法,我想知道是否有人知道这种情况的明确解决方案。
"SELECT * FROM List WHERE DateIn LIKE '%" & txtDateIn.Text & "%'"
"UPDATE [Progress] SET [Date] = '" & txtDate.Text & "'"
txtDate.Text = "" & RecordSet.Fields("Date").Value
有什么想法?提前谢谢。
**更新
其实我刚注意到我的日期时间字段中存储的日期格式为16/08/2009 00:00:00,即dd / mm / yyyy。所以也许我误解了这个问题。但是当我尝试更新日期时间值时,我得到了'将char数据类型转换为日期时间数据类型导致了超出范围的日期时间值。'。
我认为这是因为日期格式不匹配(导致月份值超出范围的问题)但是我确实在datetime字段中有日/月/年格式的日期值。提交到数据库的日期肯定是dd / mm / yyyy。
****更新2 **
好吧,我造成了一些混乱。我道歉。
在这种情况下,我有一个日期时间值(SQL Server 2005显示为16/08/2009 00:00:00),该值从数据库中读取并使用值16/08/2009填充TextBox。现在,当我尝试运行UPDATE语句而不修改TextBox文本时,我收到错误'将char数据类型转换为日期时间数据类型导致超出范围的datetime值。'
其他记录(例如日期为04/08/2009的记录)不会发生这种情况,因此我可以看到的唯一问题可能是值中的日期和月份的位置,因为如果数据库预计月份首先显然,2009年8月16日将超出范围。但是,数据库中的值已经是16/08/2009,没有任何问题。
答案 0 :(得分:9)
SQL Server没有“明显”将日期存储为mm / dd / yyyy。根据我的意识,它根本不会以文本格式存储它们。
我不知道VB6对参数化查询的支持是什么,但这就是你想要的:基本上你想将参数传递给查询作为日期而不是文本。基本上你应该将用户输入解析为一个日期(无论VB6做什么),然后在参数化查询中传递它。
编辑:我试图找出VB6如何处理参数化查询,并没有太大的运气 - 希望任何关于VB6的好书都能涵盖它。 (当然,有很多VB.NET的例子......)有一个Wrox post给出了一个例子;这可能足以让你前进。编辑:正如对此答案的评论和对此问题编辑的编辑所表明的那样,对于您的数据类型究竟是什么存在一些混淆。 请不要使用基于字符的字段来存储日期:没有好的结果。使用正确的日期/日期时间/任何字段,然后确保使用参数化查询来访问数据库,以便驱动程序可以进行任何必要的转换。完全依赖文本格式是一个坏主意。
答案 1 :(得分:5)
在查询中使用日期或时间戳的ODBC规范形式。 这样可以避免在存储日期时因本地化而产生的任何误解。 时间戳格式为{ts'yyyy-mm-dd hh:mm:ss [.fff]'} 日期格式为{d'yyyy-mm-dd'} 以下是我用于此的功能。
现在在VB6中输入和显示。理想情况下,您将使用datetimepicker控件而不是文本框,因为它返回一个日期,并且在使用它时,您选择的日期没有任何误解。但是如果你可以假设它总是DD / MM / YYYY(这是一个很大的if),你可以使用Format(datevalue,“DD / MM / YYYY”)来显示它。要将其读入日期变量,您不能只使用CDate。你需要使用解析和类似DateSerial的东西把它放在一起:DateSerial(右(strDate,4),Mid(strDate,4,2),Mid(strDate,1,2))。
' ------------------------------------------------------------------------------
' DateLiteral
'
' Description :
' given a vb date, it returns a string with the odbc canonical date format.
'
' History
' 2008-02-04 - WSR : added to this project
'
Public Function DateLiteral(ByRef dtSource As Date) As String
DateLiteral = _
"{d '" & LeftPadDigits(Year(dtSource), 4) & "-" & _
LeftPadDigits(Month(dtSource), 2) & "-" & _
LeftPadDigits(Day(dtSource), 2) & "'}"
End Function
' ------------------------------------------------------------------------------
' ------------------------------------------------------------------------------
' TimeStampLiteral
'
' Description :
' given a vb date, it returns a string with the odbc canonical timestamp format.
'
' History
' 2008-02-04 - WSR : added to this project
'
Public Function TimeStampLiteral(ByRef dtSource As Date) As String
TimeStampLiteral = _
"{ts '" & LeftPadDigits(Year(dtSource), 4) & "-" & _
LeftPadDigits(Month(dtSource), 2) & "-" & _
LeftPadDigits(Day(dtSource), 2) & " " & _
LeftPadDigits(Hour(dtSource), 2) & ":" & _
LeftPadDigits(Minute(dtSource), 2) & ":" & _
LeftPadDigits(Second(dtSource), 2) & "'}"
End Function
' ------------------------------------------------------------------------------
' ------------------------------------------------------------------------------
' LeftPadDigits
'
' Description : pads the given string to the left with zeroes if it is under
' the given length so that it is at least as long as the given length.
'
' History
' 2008-02-04 - WSR : added to this project
'
Public Function LeftPadDigits(ByVal strSource As String, ByVal lngLength As Long) As String
If Len(strSource) < lngLength Then
LeftPadDigits = String$(lngLength - Len(strSource), "0") & strSource
Else
LeftPadDigits = strSource
End If
End Function
' ------------------------------------------------------------------------------
还应该注意,是的第一选择是使用ADO和参数化查询。 在我的情况下,我通过第三方库访问数据库,不能使用参数化查询。因此日期文字处理。以下是ADO参数化查询的示例。代码可能会有所不同,具体取决于您使用的ADO连接类型:OLEDB,ODBC或SQLNative。有时它不只是一个?用于参数标记。这个例子是OLEDB。
Set cmdVerifyUser = New ADODB.Command
cmdVerifyUser.CommandType = adCmdText
cmdVerifyUser.CommandTimeout = 30
cmdVerifyUser.CommandText = "SELECT username FROM users WHERE userid = ?"
cmdVerifyUser.Parameters.Append cmdVerifyUser.CreateParameter("userid", adVarChar, adParamInput, Len(m_strUserName), m_strUserName)
cmdVerifyUser.ActiveConnection = m_conDatabase
Set rstResults = cmdVerifyUser.Execute()
If Not rstResults.EOF Then
答案 2 :(得分:0)
好吧,毕竟问题很简单。我将日期值包装在单引号(')和双引号(“)中。由于日期值不需要单引号而遇到问题。删除它们解决了问题。
无论如何,谢谢你试图帮助所有人。