Bác Tường làm hay quá, khi nào Bác chỉ giúp tôi hàm hour này với. Bữa giờ xem mà không biết cách làm giúp Bác Le Tin.Em xin góp một cách giải:Dựa vào dữ liệu của bác, em đặt 3 Name để kiểm tra dữ liệu ngày giờ như sau:![]()
Công thức để tính thời gian dự kiến kết thúc (F5:H5)
- Test1 = Sheet1!F$4 + Sheet1!F$3/24
- Test2 = (AND(HOUR(Test1)>11.5,HOUR(Test1)<13.5))*2/24 + (OR(HOUR(Test1)>17,HOUR(Test1)<7))*16.5/24
- Test3 = (WEEKDAY(Test2+Test1)=7)*44/24 - (WEEKDAY(Sheet1!F$4)=7)*2/24
= Test1 + Test2 + Test3Công thức để tính thời gian làm thực tế (F7:H7)=(F6-F4)*24 - (AND(HOUR(F6)>13.5, HOUR(F4)<11.5)*2 + (INT(F6)-INT(F4))*16.5 + (WEEKDAY(F6)=2)*11)Nhờ bác kiểm tra lại giúp em xem có đúng hay không.
Để em diễn Nôm cho bác nghe nhá. Trước tiên bác phải nắm được 2 cái này:Bác Tường làm hay quá, khi nào Bác chỉ giúp tôi hàm hour này với. Bữa giờ xem mà không biết cách làm giúp Bác Le Tin.
Bác giải thích hộ số *44/24
Cám ơn Bác nhiều!
Hu hu... Đúng là chưa chính xác.44 là số giờ từ 11:30 thứ bảy đến 7:30 sáng thứ 2
chia 24 là giờ quy ra ngày (học của ngocmaipretty), ngược lại nhân 24 là quy ngày ra giờ
nhân 44/24 là nếu WEEKDAY(Test2+Test1)=7) = "giờ kết thúc là nhằm vào thứ 7" thì cộng thêm 44 giờ
Giải thích hộ BNTT, nhưng hình như còn sai:
- test1 + test2 trúng ngày chủ nhật thì sao?
- test1 + test2 trúng ngày thứ bảy, nhưng vào buổi sáng thì sao?
- trừ 2 giờ để làm gì?
Chắc phải cầu cứu lại Ms. NgocMai!
Mấy con số 11.5, 13.5, 17, 7 chắc bác đoán được là gì chớ?
Dạ đúng là như vậy. Chưa chính xác. Em đang nghiên cứu lại nó, vì quả thật là ... hơi khó nhai!Cảm ơn bạn BNTT ,nhưng chưa ổn ,Ví dụ nhập 41.5 thì phải cách đúng 1 tuần sau (vì 1 tuần làm 41.5 giờ) chứ
Bài toán dạng này không phải là KHÓ, mà là CỰC KHÓDạ đúng là như vậy. Chưa chính xác. Em đang nghiên cứu lại nó, vì quả thật là ... hơi khó nhai!
Quả đúng là Cực Khó!Bài toán dạng này không phải là KHÓ, mà là CỰC KHÓ
Tôi thì nghĩ vầy:Quả đúng là Cực Khó!
Em nghĩ rằng chắc không dùng công thức nổi, giả như có nổi đi nữa thì chắc cái công thức này sẽ dài khủng khiếp, và phải rất nhiều công thức thì mới có thể chơi nổi!
Em có ý tưởng này, dùng VBA. Nhưng em thì không giỏi về VBA, nên xin nêu ra ý tưởng thôi, các bác xem có khả thi không thì làm dùm...
Lấy thời gian bắt đầu + thời gian dự định sẽ hoàn thành công việc, ra kết quả là A chẳng hạn. Rồi dùng vòng lặp để kiểm tra kết quả A:
(Các điều kiện kiểm tra trên có thể còn thiếu... em chỉ ví dụ thôi)
- Nếu A rơi vào khoảng nghỉ trưa (tử 11:30 đến 13:30) thì cộng thêm 2 tiếng. Cho ra A1.
- Nếu A1 rơi vào khoảng nghỉ chiều (từ 17:00 đến 7:30 ngày hôm sau) thì cộng thêm 14,5 tiếng. Cho ra A2.
- Nếu A2 rơi vào trưa thứ 7 (sau 11:30) thì cộng thêm 44 tiếng, cho ra A3.
- Rồi lại quay vòng tiếp, nếu A3 rơi vào khoảng nghỉ trưa thì lại cộng thêm 2 tiếng
- V.v...
- Cho tới khi nào cái kết quả này nằm trong khoảng thời gian chấp nhận được (rơi vào trong giờ hành chánh) thì dừng lại.
Liệu có khả thi không ạ ?
Em làm thử 1 function EstEndDate dự kiến ngày kết thúc. Anh xem thử có OK, em làm tiếp phần kia.Tôi gởi file nhờ các bạn xem giúp tối ưu hóa , mới tập viết code ,nhưng thấy nhiều IF quá , và chưa phát hiện sai .
Tôi đã làm tìm thời gian thực tế (Chưa biết ổn không), còn thời gian dự định chưa làm được , mời các bạn động não tiếp . Cảm ơn
Function EstEndTime(NgayDau As Variant, SoPhut As Long)
Dim NgayCuoi As Variant, iPhut As Long, IntervalType As String
IntervalType = "n"
SoPhut = SoPhut * 60
If Weekday(NgayDau) = 1 Then Exit Function 'xem lai cac dieu kien ve t7, CN
If Not IsDate(NgayDau) Then Exit Function
If SoPhut = 0 Then
EstEndTime = NgayCuoi
Exit Function
End If
iPhut = 30
Do While Not iPhut = SoPhut + 30
NgayCuoi = DateAdd(IntervalType, 30, NgayDau)
If Weekday(NgayDau) <> 7 And Hour(NgayCuoi) = 11 And Minute(NgayCuoi) = 30 And iPhut < SoPhut Then
NgayDau = DateAdd(IntervalType, 120, NgayCuoi)
ElseIf Weekday(NgayDau) <> 7 And Hour(NgayCuoi) = 17 And Minute(NgayCuoi) = 0 And iPhut < SoPhut Then
NgayDau = DateAdd(IntervalType, 14 * 60 + 30, NgayCuoi)
ElseIf Weekday(NgayDau) = 7 And Hour(NgayCuoi) = 11 And Minute(NgayCuoi) = 30 And iPhut < SoPhut Then
NgayDau = DateAdd(IntervalType, 44 * 60, NgayCuoi)
Else
NgayDau = NgayCuoi
End If
iPhut = iPhut + 30
Loop
EstEndTime = NgayCuoi
End Function
Chạy sub sau thì OK mà chưa hiểu sao chuyển sang UDF thì sai ở giờ end la 11h30Hình như là số giờ chứ không phải số phút
Và chỉ OK đối với số giờ chẵn .
Sub EndTime()
Dim NgayDau, NgayCuoi, iPhut As Long
With Application
.Calculation = xlCalculationManual
End With
Dim SoPhut As Long
Dim IntervalType As String
Sheet2.Select
IntervalType = "n"
NgayDau = Cells(2, 2)
SoPhut = Cells(1, 2) * 60
If Weekday(NgayDau) = 1 Then Exit Sub 'xem lai thu sau
iPhut = 30
Do While Not iPhut = SoPhut + 30
NgayCuoi = DateAdd(IntervalType, 30, NgayDau)
If Weekday(NgayDau) <> 7 And Hour(NgayCuoi) = 11 And Minute(NgayCuoi) = 30 And iPhut < SoPhut Then
NgayDau = DateAdd(IntervalType, 120, NgayCuoi)
ElseIf Weekday(NgayDau) <> 7 And Hour(NgayCuoi) = 17 And Minute(NgayCuoi) = 0 And iPhut < SoPhut Then
NgayDau = DateAdd(IntervalType, 14 * 60 + 30, NgayCuoi)
ElseIf Weekday(NgayDau) = 7 And Hour(NgayCuoi) = 11 And Minute(NgayCuoi) = 30 And iPhut < SoPhut Then
NgayDau = DateAdd(IntervalType, 44 * 60, NgayCuoi)
Else
NgayDau = NgayCuoi
End If
iPhut = iPhut + 30
Loop
Cells(2, 3) = NgayCuoi
End Sub
Bạn nghiên cứu hàm DateAdd nó cũng tựa như hàm Datedif.Chưa ổn lắm nhưng không hiểu ý nghĩa mấy chữ trong câu này nên cũng chưa biết nên sửa thế nào : NgayDau = DateAdd(IntervalType, 120, NgayCuoi)
Mình nói rõ thêm là Giờ định mức ấy có thể là : 10 ph ,15 ph , ... 30 ph,35 ph...1 g ,..
Function EndTime(NgayDau As Variant, SoPhut As Double)
Dim NgayCuoi As Variant, iPhut As Double, Block As Long
SoPhut = SoPhut * 60 'xem lai neu 1h5' thi nhap so the nao'
If Weekday(NgayDau) = 1 Then Exit Function 'xem lai cac dieu kien ve t7, CN'
If Not IsDate(NgayDau) Then Exit Function
Block = 30
If SoPhut = 0 Then
EndTime = NgayCuoi
Exit Function
End If
iPhut = Block
Do While Not iPhut = SoPhut + Block
NgayCuoi = DateAdd("n", Block, NgayDau)
If Weekday(NgayDau) <> 7 And Hour(NgayCuoi) = 11 And Minute(NgayCuoi) = 30 Then
NgayDau = DateAdd("n", 120, NgayCuoi)
ElseIf Weekday(NgayDau) <> 7 And Hour(NgayCuoi) = 17 And Minute(NgayCuoi) = 0 Then
NgayDau = DateAdd("n", 14 * 60 + 30, NgayCuoi)
ElseIf Weekday(NgayDau) = 7 And Hour(NgayCuoi) = 11 And Minute(NgayCuoi) = 30 Then
NgayDau = DateAdd("n", 44 * 60, NgayCuoi)
Else
NgayDau = NgayCuoi
End If
iPhut = iPhut + Block
Loop
EndTime = NgayCuoi
End Function