Put weeknum in an array? - excel

Here is what im trying to do: Cell B2: Start Date and Cell B3: End Date
Example:
B2 --> 01/01/2019
B3 --> 01/03/2019
I would like to get all the week numbers and put them in an array
Here is a picture of the Excel cells
Here is my code so far
Application.ScreenUpdating = False
Application.DisplayAlerts = False
Dim StartD As Date, EndD As Date
Set wks = ThisWorkbook.Sheets("Foglio1")
Worksheets("Foglio1").Range("D2:XZ39").Clear
StartD = Worksheets("Foglio1").Cells(2, 2)
EndD = Worksheets("Foglio1").Cells(3, 2)
I would like to loop though the given two dates: 01/01/2019 , 01/03/2019 get the week numbers and put them in an array(if it's possible)
So my output would be:
Array(1, 2, 3, 4, 5, 6, 7, 8, 9) --> Since between January and March there are 9 weeks

If you do not want Calendar Weeks and want to include a week even if there is one day from it then you can try this.
Logic
It finds when the next week is starting. So default number of weeks is 1.
Loops and counts the number of days (Say Monday and then Tuesday and so on) between two dates and whichever is highest, it returns it and adds it to 1.
Also there is no need to loop and create an array. You can create a sequential array in One Go
Code
Option Explicit
Sub Sample()
Dim WeeksCount As Long
Dim CurCount As Long
Dim countOfWeeks As Long
Dim i As Long, tmpCount As Long
Dim sDate As Date, eDate As Date
sDate = DateSerial(2019, 1, 6)
eDate = DateSerial(2019, 1, 8)
If Weekday(sDate, vbMonday) <> 1 Then
sDate = DateAdd("d", 7 - Weekday(sDate, vbMonday) + 1, sDate)
WeeksCount = 1
End If
For i = 1 To 7
CurCount = GetMeMyKindOfWeeksTotal(sDate, eDate, i)
If tmpCount < CurCount Then tmpCount = CurCount
Next i
WeeksCount = WeeksCount + tmpCount
Dim MyArray
MyArray = Evaluate("Row(1" & ":" & WeeksCount & ")")
If WeeksCount = 1 Then
Debug.Print MyArray(1)
Else
For i = LBound(MyArray) To UBound(MyArray)
Debug.Print MyArray(i, 1)
Next i
End If
End Sub
Private Function GetMeMyKindOfWeeksTotal(ByVal sDate As Date, ByVal eDate As Date, dy As Long)
Dim j As Long
Dim TotalDays As Long
For j = sDate To eDate
If Weekday(j) = dy Then
TotalDays = TotalDays + 1
End If
Next
GetMeMyKindOfWeeksTotal = TotalDays
End Function
Various Tests
sDate = DateSerial(2019, 1, 6)
eDate = DateSerial(2019, 1, 8)
This will give you 2
sDate = DateSerial(2019, 1, 1)
eDate = DateSerial(2019, 3, 1)
This will give you 9
sDate = DateSerial(2019, 1, 1)
eDate = DateSerial(2019, 1, 1)
This will give you 1
sDate = DateSerial(2019, 1, 1)
eDate = DateSerial(2019, 1, 8)
This will give you 2

You could use something like the following
Option Explicit
Sub Sample()
Dim sDate As Date, eDate As Date
Dim NoOfWeeks As Long
Dim arr As Variant
Dim i As Long
With Worksheets("Foglio1")
sDate = .Range("B2")
If Weekday(sDate, vbMonday) <> 1 Then
sDate = DateAdd("d", 7 - Weekday(sDate, vbMonday) + 1, sDate)
NoOfWeeks = 1
End If
eDate = .Range("B3")
End With
If sDate = eDate Then
NoOfWeeks = NoOfWeeks + 1
Else
NoOfWeeks = NoOfWeeks + WorksheetFunction.RoundUp((eDate - sDate) / 7, 0)
End If
ReDim arr(1 To NoOfWeeks)
For i = 1 To NoOfWeeks
arr(i) = i
Next i
MsgBox Join(arr, ";")
End Sub

You can define a UDF like below:
Public Function GetWeekNums(startDate As Date, endDate As Date, Optional varDelim As Variant)
Dim lngStartWeek As Long
Dim lngEndWeek As Long
Dim i As Long
If IsMissing(varDelim) Then varDelim = ","
lngStartWeek = Application.WorksheetFunction.WeekNum(startDate)
lngEndWeek = Application.WorksheetFunction.WeekNum(endDate)
For i = lngStartWeek To lngEndWeek
GetWeekNums = GetWeekNums & " " & i
Next
GetWeekNums = Replace(Trim(GetWeekNums), " ", varDelim & " ")
End Function
and then use it in workbook like:
=GetWeekNums(B2,B3,";")

If someone prefers just a worksheet formula, you can use:
=ROW(INDEX($A:$A,WEEKNUM($B$2),1):INDEX($A:$A,WEEKNUM($B$3),1))
Depending on when your week starts, use the appropriate return_type argument for the function.

Related

How to get the total of every monday to saturday or tuesday to sunday in a month dynamically

I am trying to figure out how to get the the total of days in a month like for every monday to saturday or tuesday to sunday then multiply by working hours. It depends on the user if what they like to input in cell. However, the CALCULATION it depends on the date where the user input either in textbox or cell.
For X = 2 To lastRow
val = ThisWorkbook.Sheets("Input").Cells(X, 2).Value
If UCase(val) Like "*TO*" Then
Dim numStringTo As Integer
Dim strToDays() As String
Dim wordToCount As Long
numStringTo = 3
strToDays = VBA.Split(val, " ")
wordToCount = UBound(strToDays)
whEveryDay = ThisWorkbook.Sheets("Input").Cells(X, 4).Value
whEveryDay = whEveryDay * Weekday(nb_days, 6)
Debug.Print "Every = " & whEveryDay
End If
Next X
I need to get the total of days in a month and multiply by working hours. As of now we are in January 2023 and the pattern for January is 2-7,9-14,16-21,23-28,30-31 and the patter for November 2022 is 1-5,8-12,15-19,22-26,29-30.
For example:
Days
Date
Working Hours
every Monday to Saturday
2-7,9-14,16-21,23-28,30-31
1.2
every Tuesday to Saturday
1-5,8-12,15-19,22-26,29-30
0.5
Example of calculation:
Days * Working hours
And I need the calculation dynamically like for example if I change the cell of "every Monday to Saturday" to "every Wednesday to Monday" so, the count of days in a month will be also dynamically.
Thanks in advance,
James
Option Explicit
Sub demo()
Dim lastrow As Long, r As Long, s As String, dt As Date
s = InputBox("Input Date")
If IsDate(s) Then
dt = CDate(s)
Else
MsgBox s & " not a date", vbCritical
Exit Sub
End If
With ThisWorkbook.Sheets("Input")
lastrow = .Cells(.Rows.Count, "B").End(xlUp).Row
For r = 2 To lastrow
s = .Cells(r, "B").Value
If UCase(s) Like "*TO*" Then
' total days in column E
.Cells(r, "E") = mydatecalc(dt, s)
' hrs per day * days
.Cells(r, "F").FormulaR1C1 = "=RC[-2]*RC[-1]"
End If
Next
End With
MsgBox "Calc done for " & Format(dt, "mmm yyyy")
End Sub
Function mydatecalc(dtNow As Date, s As String) As Long
Dim m As Integer, s1 As String, s2 As String, d As String
Dim dt As Date, dtStart As Date, dtEnd As Date
Dim n As Integer, ar, bCount As Boolean, msg As String
m = Month(dtNow) ' input month
dtStart = DateSerial(Year(dtNow), m, 1)
dtEnd = DateAdd("m", 1, dtStart) - 1
ar = Split(s, " ")
s1 = Left(ar(1), 3)
s2 = Left(ar(3), 3)
For dt = dtStart To dtEnd
d = Format(dt, "ddd")
If d = s1 Then bCount = True
If bCount Then
n = n + 1
msg = msg & vbLf & n & " " & Format(dt, "ddd dd")
End If
If d = s2 Then bCount = False
Next
'MsgBox s & " = " & n & " days in " & Format(dtNow, "mmm yyyy") & msg
mydatecalc = n
End Function
You could achieve that with a formula as well (Excel 365) and the following setting:
=LET(monthDays,SEQUENCE(EDATE(A2,1)-A2,1,A2),
weekdays,FILTER(SEQUENCE(1,7),B2:H2<>""),
workingHours,I2,
workedDays,FILTER(monthDays,ISNUMBER(MATCH(WEEKDAY(monthDays,2),weekdays,0))),
COUNT(workedDays)*workingHours)
Please, test the next solution. The range to be processed starts from column B:B and the return will be done in E:E. The code assumes that all strings in B:B contain the necessary data of pattern "every 'day name' to 'day name'":
Sub getHours()
Dim ws As Worksheet, lastR As Long, arr, i As Long, curDate As Date
curDate = Date 'use here your date where from to extract the month
Set ws = ActiveSheet
lastR = ws.Range("B" & ws.rows.count).End(xlUp).Row
arr = ws.Range("B2:E" & lastR).Value2
For i = 1 To UBound(arr)
arr(i, 4) = TotalHoursPerDaysGroup(CStr(arr(i, 1)), curDate, CDbl(arr(i, 3)))
Next i
ws.Range("B2:E" & lastR).Value2 = arr
End Sub
Function TotalHoursPerDaysGroup(val As String, curDay As Date, workingH As Double) As Double
Dim curMonth As Long, startDN As String, endDN As String, nb_days As Long
Dim dtStart As Date, dtEnd As Date, dayN As String, d As Date, arrND, boolCount As Boolean
'Dim arrDaysRo: arrDaysRo = Split("lun.,mar.,mie.,joi,vin.,sâm.,dum.", ",") 'localized days name...
'Dim arrDaysEn: arrDaysEn = Split("Mon,Tue,Wen,Thu,Fry,Sat,Sun", ",")
curMonth = Month(curDay) ' current month
dtStart = DateSerial(Year(curDay), curMonth, 1)
dtEnd = WorksheetFunction.EoMonth(dtStart, 0)
arrND = Split(val, " ")
startDN = left(arrND(1), 3)
endDN = left(arrND(3), 3)
For d = dtStart To dtEnd
dayN = Format(d, "ddd")
If dayN = startDN Then boolCount = True
'If arrDaysEn(Application.match(dayN, arrDaysRo, 0) - 1) = startDN Then boolCount = True
If boolCount Then
nb_days = nb_days + 1
End If
If d = endDN Then boolCount = False
'If arrDaysEn(Application.match(dayN, arrDaysRo, 0) - 1) = endDN Then boolCount = False
Next d
TotalHoursPerDaysGroup = nb_days * workingH
End Function
I tried using first three characters of the days name, but because of localization, I couldn't, so I created two equivalence arrays to overpass the problem. I let them in the function, just in case...
If no such a problem, you can comment the lines making the equivalence and uncomment the ones above them. I can see that my solution used in the function is very similar with the one already posted...

Build a List with dates in a for loop VBA

I am trying to build a loop which prints a list with the 15th day and the last day of each month. The starting date of the list will depend on the current day (num_day), whereas the length of such list will depend on a given N number.
For example, if today is 30/07/2021 (dd/mm/yyyy format), and the N = 5 the list should be the following:
31/07/2021, 15/08/2021, 31/08/2021, 15/09/2021, 30/09/2021
My current VBA code is the following:
Sub print_dates()
N = 9
For i = 0 To N - 1
curr_day = DateAdd("m", i, Date)
num_day = Format(Date, "dd")
If num_day <= 15 Then
If i Mod 2 = 0 Then
print_day = "15/" & Format(curr_day, "mm") & "/" & Format(curr_day, "yyyy")
Else
print_day = DateSerial(Year(curr_day), Month(curr_day), 0)
End If
Else
If i Mod 2 = 0 Then
print_day = DateSerial(Year(curr_day), Month(curr_day), 0)
Else
print_day = "15/" & Format(curr_day, "mm") & "/" & Format(curr_day, "yyyy")
End If
End If
Debug.Print print_day
Next i
End Sub
With my current code the result of the list is:
30/06/2021
15/08/2021
31/08/2021
15/10/2021
31/10/2021
15/12/2021
31/12/2021
15/02/2022
28/02/2022
The months with odd numbers (7, 9, 11, etc.) are being skipped by the code. Also, the list starts with last month's last day.
Are there any suggestions on how to reach the desired result?
Thanks a lot in advance.
One more:
Sub print_dates()
Dim dt As Date, i As Long
dt = Date
For i = 1 To 10
dt = NextDate(dt)
Debug.Print dt
Next i
End Sub
'next date either 15th or last day of month
Function NextDate(ByVal dt As Date)
Dim d As Long, ld As Long, m As Long, y As Long
d = Day(dt)
m = Month(dt)
y = Year(dt)
ld = Day(Application.EoMonth(dt, 0)) 'last day of the month
NextDate = IIf(d < 15, DateSerial(y, m, 15), _
IIf(d < ld, DateSerial(y, m, ld), DateAdd("d", 15, dt)))
End Function
The function below will return the list you want in an array of real dates.
Function DateList(ByVal Dstart As Date, _
ByVal Months As Integer) As Date()
' 300
Dim Fun() As Date ' list of dates
Dim i As Long ' index of Fun()
Dim NextDate As Date
Dim n As Integer ' loop counter: Months
ReDim Fun(1 To Months * 2)
If Day(Dstart) < 15 Then
i = 1
Fun(i) = DateSerial(Year(Dstart), Month(Dstart), 15)
End If
NextDate = DateSerial(Year(Dstart), Month(Dstart) + 1, 1)
For n = 1 To Months
i = i + 1
Fun(i) = NextDate - 1
If i < UBound(Fun) Then
i = i + 1
Fun(i) = DateAdd("d", 14, NextDate)
NextDate = DateAdd("m", 1, NextDate)
End If
Next n
DateList = Fun
End Function
The function takes two arguments. The first date and the number of years. The first date need not be an ultimo or 15th because the function will determine the next available. Therefore you might call the function from your program as shown below.
Private Sub Test_PrintDates()
' 300
Dim MyList() As Date
Dim f As Long
MyList = DateList(Date + 2, 3)
For f = LBound(MyList) To UBound(MyList)
Debug.Print Format(MyList(f), "ddd, mmmm dd, yyyy")
Next f
End Sub
As you see, I used Date + 2 as the first date (Dstart) to test various start dates. The resulting list can be printed in any valid date format as demonstrated above.
Would something like this work better?
Sub print_dates()
Dim N As Long, num_day As Long
Dim curr_day As String, print_day As String
N = 5
For i = 1 To N / 2 + 0.5 Step 0.5 '<- Half step with compensation to N
curr_day = DateAdd("m", i, Date)
num_day = Format(Date, "dd")
If num_day <= 15 Then
If Int(i) / i = 1 Then '<- check for whole numbers instead
print_day = "15/" & Format(curr_day, "mm") & "/" & Format(curr_day, "yyyy")
Else
curr_day = DateAdd("m", i + 1, Date) '<- random fix
print_day = DateSerial(Year(curr_day), Month(curr_day), 0)
End If
Else
If Int(i) / i = 1 Then '<- same change here
print_day = DateSerial(Year(curr_day), Month(curr_day), 0)
Else
print_day = "15/" & Format(curr_day, "mm") & "/" & Format(curr_day, "yyyy")
End If
End If
Debug.Print print_day
Next i
End Sub
Following is an array function.
Option Explicit
Function HalfMonthDateSeries(myDate As Date, count As Long)
'Array (Contrl+Shift+Enter CSE) function
'returns one dimensional array of dateserial 15th and EOM from myDate
'While entering in a column wrap this function in transpose function
Dim arr(), i As Long
ReDim arr(count - 1) 'being 0 based one dimensional array
For i = LBound(arr) To UBound(arr)
If i = LBound(arr) Then
arr(i) = IIf(Day(myDate) <= 15, DateSerial(Year(myDate), _
Month(myDate), 15), WorksheetFunction.EoMonth(myDate, 0))
Else
arr(i) = IIf(Day(arr(i - 1)) = 15, _
WorksheetFunction.EoMonth(arr(i - 1) + 1, 0), arr(i - 1) + 15)
End If
Next i
HalfMonthDateSeries = arr
End Function
In procedure
Sub Print_HalfMonthDateSeries()
Dim arr, i As Long
arr = HalfMonthDateSeries(Date, 5)
' or arr = HalfMonthDateSeries(#7/13/2021#, 5)
For i = LBound(arr) To UBound(arr)
Debug.Print CDate(arr(i))
' or Cells(i + 2, 1) = CDate(arr(i))
Next i
End Sub

How to get the Mondays (full date) in the current month?

I am trying to get all the dates for the Mondays in the current month. For example, in the current month May 2021 we would have: 3/05/2021, 10/05/2021, 17/05/2021, 24/05/2021, 31/05/2021.
On investigation I found this answer for an older question which helps to
Calculate the number of weeks in a month, however this shows 6 as an answer. Which is correct (See shared calendar). However I wish to count only the Mondays on the month.
I also have a complementary code which gives me the number of Mondays in the month:
Sub NumMondays()
Dim i As Integer
Dim num_mondays As Integer
Dim test_date As Date
Dim orig_month As Integer
month_name = Format(Date, "mmmm")
year_name = Format(Date, "yyyy")
' Get the first day of the month.
test_date = CDate(month_name & " 1, " & year_name)
' Count the Mondays.
orig_month = Month(test_date)
Do
num_mondays = num_mondays + 1
test_date = DateAdd("ww", 1, test_date)
Loop While (Month(test_date) = orig_month)
Debug.Print test_date
Debug.Print orig_month
Debug.Print num_mondays
End Sub
Such code prints 5 for number of Mondays, however I have been unable to convert this to the actual dates of such Mondays. Any suggestions?
Thanks a lot in advance
A Functional Solution
A good approach is to use a function that will return a collection of the days from a specified month.
This is similar to other approaches provided — however, this adds a bit of performance and more importantly intellisense for the day of the week.
Public Function GetMonthDays(dayToGet As VbDayOfWeek _
, monthToGetFrom As Long _
, yearToGetFrom As Long) As Collection
Set GetMonthDays = New Collection
' First Starting date, and will be used
' for incrementing to next date/next day.
Dim nextDate As Date
nextDate = DateSerial(yearToGetFrom, monthToGetFrom, 1)
' Loop until month changes to next month.
Do While month(nextDate) = monthToGetFrom
' If weekday matches, then add and
' increment to next week (7 days)
If Weekday(nextDate) = dayToGet Then
GetMonthDays.Add nextDate
nextDate = nextDate + 7
' Day did not match, therefore increment
' 1 day until it does match.
Else
nextDate = nextDate + 1
End If
Loop
End Function
Example
Here is a basic example of how to use it.
Sub testGetMonthDays()
Dim mondayDate As Variant
For Each mondayDate In GetMonthDays(vbMonday, month(Date), year(Date))
Debug.Print mondayDate
Next
End Sub
5/3/2021
5/10/2021
5/17/2021
5/24/2021
5/31/2021
Try the next code, please:
Sub NumMondays()
Dim i As Long, month_name, year_name, num_mondays As Integer
Dim test_date As Date, orig_month As Integer, arrMondays, k As Long
month_name = Format(Date, "mmmm")
year_name = Format(Date, "yyyy")
' Get the first day of the month.
test_date = CDate(month_name & " 1, " & year_name)
orig_month = month(test_date)
ReDim arrMondays(4)
'extract and count Mondays:
Do
If Weekday(test_date, vbMonday) = 1 Then
arrMondays(k) = test_date: k = k + 1: num_mondays = num_mondays + 1
End If
test_date = test_date + 1
Loop While (month(test_date) = orig_month)
ReDim Preserve arrMondays(k - 1)
Debug.Print "Current month no = " & orig_month
Debug.Print "No of Mondays = " & num_mondays
Debug.Print Join(arrMondays, ", ")
End Sub
Brute force approach
Sub tester()
Dim dt
For Each dt In GetDayDates(2021, 5, "Mon")
Debug.Print dt
Next dt
End Sub
Function GetDayDates(yr As Long, mon As Long, d As String)
Dim dt As Date, col As New Collection
dt = DateSerial(yr, mon, 1)
Do While Month(dt) = mon
If Format(dt, "ddd") = d Then col.Add dt
dt = dt + 1
Loop
Set GetDayDates = col
End Function
Different approach. There is a somewhat known Excel formula that provides the Monday of a Given Weeknumber and Year (=DATE(A2, 1, -2) - WEEKDAY(DATE(A2, 1, 3)) + B2 * 7) [A2 is the Year, B2 is the Weeknumber]. In this case I loop all weeks on a month and use that formula on each week.
Sub CaseOfTheMondays()
Dim inDate As Date, sDate As Date, eDate As Date, sYear As Date, mDate As Date
Dim cMonth As Integer, i As Integer, x As Integer
inDate = InputBox("Enter a valid date")
If IsDate(inDate) Then
ThisWorkbook.Worksheets(1).Columns("A").ClearContents
sDate = DateAdd("d", -(Format(inDate, "d") - 1), inDate)
eDate = DateAdd("m", 1, inDate) - (Format(inDate, "d") + 1)
sYear = DateAdd("m", -(Format(inDate, "m") - 1), DateAdd("d", -(Format(inDate, "d") - 1), inDate))
cMonth = Format(inDate, "m")
sWeek = WorksheetFunction.WeekNum(sDate, vbMonday)
eWeek = WorksheetFunction.WeekNum(eDate, vbMonday)
x = 1
For i = sWeek To eWeek
mDate = DateAdd("d", -3, sYear) - Weekday(DateAdd("d", 2, sYear)) + (i * 7)
If Format(mDate, "m") = cMonth Then
ThisWorkbook.Worksheets(1).Cells(x, 1).Value = mDate
x = x + 1
End If
Next i
Else
MsgBox "invalid date"
End If
End Sub

VBA Convert Date

What am I doing wrong ?
in cell a2 I have a date (US) format 19790131. I would like to have this rewritten in 31.01.1979 enter code hereBut get the result: 1/31/1979
For i = 2 To z
DatText = Cells(i, x)
Cells(i, x) = CDate(Mid(DatText, 7, 2) & "." & Mid(DatText, 5, 2) & "." & Mid(DatText, 1, 4))
Cells(i, x).NumberFormat = "dd.mm.yyyy"
Next i
Use slashes instead of periods so CDate will understand it.
Cells(i, x) = CDate(Mid(DatText, 7, 2) & "/" & Mid(DatText, 5, 2) & "/" & Mid(DatText, 1, 4))
If the date is a "real" Excel date, with a cell format of "yyyymmdd", then you just need to change the cell format to "dd.mm.yyy"
If the date is the actual number: 19790131, then you have to convert it first to a real date. Try:
Function dtNumToDt(n As Long) As Date
Dim yr As Long, mn As Long, dy As Long
yr = Left(n, 4)
mn = Mid(n, 5, 2)
dy = Right(n, 2)
dtNumToDt = DateSerial(yr, mn, dy)
End Function
And then format the cell (numberformat) as "dd.mm.yyy"
You can use Format for this - and include IsDate for a little error handling:
Public Function ConvertDate()
Dim ThisCell As Excel.Range
Dim RowIndex As Long
Dim ColumnIndex As Long
Dim DatText As String
ColumnIndex = 1
For RowIndex = 2 To 10
Set ThisCell = Cells(RowIndex, ColumnIndex)
If Not IsDate(ThisCell.Value) Then
DatText = Format(ThisCell.Value, "####\/##\/##")
If IsDate(DatText) Then
ThisCell.Value = CDate(DatText)
End If
End If
Next
End Function

Get all weeknums from 2 input dates and put them in an array?

Since I asked a wrong question in the last post, but still improved a lot (I already created a Planning table in Excel, if someone want it I will be happy to share), here is what im trying do to: Cell B2: Start Date and Cell B3: End Date
Example:
B2 --> 11/03/2019
B3 --> 22/04/2019
Here is my code so far with the help of this community
Option Explicit
Sub Sample()
Dim sDate As Date, eDate As Date
Dim NoOfWeeks As Long
Dim arr As Variant
Dim i As Long
Dim myCellToStart As Range
Set myCellToStart = Worksheets(1).Range("D4")
Dim myVar As Variant
Dim myCell As Range
Set myCell = myCellToStart
With Worksheets("Foglio1")
sDate = .Range("B2")
If Weekday(sDate, vbMonday) <> 1 Then
sDate = DateAdd("d", 7 - Weekday(sDate, vbMonday) + 1, sDate)
NoOfWeeks = 1
End If
eDate = .Range("B3")
End With
If sDate = eDate Then
NoOfWeeks = NoOfWeeks + 1
Else
NoOfWeeks = NoOfWeeks + WorksheetFunction.RoundUp((eDate - sDate) / 7, 0)
End If
ReDim arr(1 To NoOfWeeks)
For i = 1 To NoOfWeeks
arr(i) = i
Next i
End Sub
Basically with my current code I would obtain an array with this ouput: arr(1, 2, 3, 4, 5, 6)
Related to this --> See Calendar
I would like to obtain: arr(11, 12, 13, 14, 15, 16, 17)
Using Application.WeekNum will be much more simple:
Option Explicit
Sub Test()
Dim StartDate As Date, EndDate As Date
With ThisWorkbook.Sheets("Foglio1") 'remember to fully qualify your ranges, including the workbook
StartDate = .Range("B2")
EndDate = .Range("B3")
End With
Dim StartWeek As Long, EndWeek As Long
StartWeek = Application.WeekNum(StartDate, 2)
EndWeek = Application.WeekNum(EndDate, 2)
Dim arr
Dim i As Long
ReDim arr(StartWeek To EndWeek)
For i = StartWeek To EndWeek
arr(i) = i
Next
End Sub
This is an alternative way:
Sub Test()
Dim StrtD As Long, EndD As Long
Dim arr As Variant
With Sheets("Foglio1")
StrtD = Application.WeekNum(.Cells(1, 2).Value, 2)
EndD = Application.WeekNum(.Cells(2, 2).Value, 2)
arr = Application.Transpose(.Evaluate("ROW(" & StrtD & ":" & EndD & ")"))
End With
End Sub
The Application.Transpose() creates an 1-D array you can call through arr(x) where x is any position within the array. You can leave the transpose if you want to create a 2-D array.
To not use .Transpose but use .Columns to return a 1-D array you can tweak the code to:
Sub Test()
Dim StrtD As Long, EndD As Long
Dim arr As Variant
With Sheets("Foglio1")
StrtD = Application.WeekNum(.Cells(1, 2).Value, 2)
EndD = Application.WeekNum(.Cells(2, 2).Value, 2)
arr = .Evaluate("COLUMN(" & .Cells(1, StrtD ).Address & ":" & .Cells(1, EndD ).Address & ")")
End With
End Sub
I guess it's a matter of preference as both ways will return an array > arr(11, 12, 13, 14, 15, 16, 17)

Resources