Start time "08:58"
, end time "17:37"
. Expected result is 8.39 meaning elapsed time of 8 hours and 39 minutes. I tried this:
Function UDF_datediff(d1 As Date, d2 As Date) As Double
Dim hours As Integer
Dim minutes As Integer
hours = DateDiff("h", d1, d2)
minutes = (DateDiff("n", d1, d2) Mod 60)
UDF_datediff = hours + minutes / 100
End Function
But it calculates wrong results for hours. Surprisingly! Would you share any suggestion to calculate expected results?
Try this:
Sub Test()
Dim minutes As Long
Dim d1 As Date, d2 As Date
d1 = "2018-01-01 08:58:00"
d2 = "2018-01-01 17:37:00"
minutes = DateDiff("n", d1, d2)
' Will print 8.39
MsgBox Int(minutes / 60) & "." & minutes Mod 60
End Sub
Function UDF_datediff(d1 As Date, d2 As Date) As Double
Dim difference AS Double
difference = d2 - d1
UDF_datediff = Sgn(difference) * CDbl(Format(difference , "hh.mm"))
End Function
In your example, d2 - d1 is a DateTime of 1899-12-30 08:37:00
- Format this as Hours (2 digits), decimal point, Minutes (2 digits), then convert to a double and correct the sign.
Try
Sub test()
Dim d1 As Date, d2 As Date
Dim m As Double
d1 = TimeValue("08:58")
d2 = TimeValue("17:37")
m = UDF_datediff(d1, d2)
MsgBox m
MsgBox Format(m / 24, "hh:mm")
End Sub
UDF
Function UDF_datediff(d1 As Date, d2 As Date) As Double
UDF_datediff = (d2 - d1) * 24
End Function
DateDiff
is actually not quite needed. You may use a simple "minus" to see what's going on:
Sub TestMe()
With Worksheets(1)
Dim d1 As Date: d1 = 0.373611111111111 '08:58:00
Dim d2 As Date: d2 = 0.734027777777778 '17:37:00
End With
Debug.Print UdfDatediff(d1, d2) '08:39:00
End Sub
Function UdfDatediff(d1 As Date, d2 As Date) As Date
UdfDatediff = Abs(d1 - d2)
End Function
The date in VBA is presented as a double number. Thus, if you write 0.373611111111111 and format it to in Date in VBA you would get:
?CDate(0.373611111111111)
08:58:00
The double values above are obtained through writing the following in the Immediate Window Ctrl + G :
?CDbl(TimeSerial(8,58,0))
0,373611111111111
In Excel, the date is also presented as a double number, but for the first two months of the year 1900 it is a bit deviating from the date in VBA (See the question of BillG here ).
alternatively - given that times are stored as decimal fractions of a day
Function UDF_datediff(d1 As Date, d2 As Date) As Double
d2 = d2-int(d2) 'remove date portion
d1= d1 - int(d1)
UDF_datediff = (d2-d1)*24
End Function
The general answer is this:
Format(CDate(d2-d1),"h:m")
For your Start and End times in particular, this expression will produce the "8:39" result.
If you need to extract hours and minutes from this, you can do this:
Dim sDuration as String
Dim iCol as Long
Dim sH as String
Dim sM as String
Dim iH as Long
Dim iM as Long
sDuration = Format(CDate(d2-d1),"h:m") ' the "8:39" in your case
iCol =InStr(sDuration, ":")
sH = Left(sDuration, iCol - 1)
sM = Mid(sDuration, iCol + 1, 2) ' length of 2 or any longer
iH = CInt(sH)
iM = CInt(sM)
You can always work with the "numbers", converting decimals, multiplying by 24 and by 60, rounding... as in
iH = Int(CDate(d2-d1)*24) ' to get the hours
etc. (it's a bit more complicated with Minutes)
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.