I'm having some troubles doing something easy: checking the most recent date in an array. I create an array of webelements. There are some dates in this array in "fixed" places and I want to take the most recent of them.
This is what I'm doing:
Set cc = Description.Create
cc("micclass").value="WebElement"
cc("name").value="arrow_down"
Set collcc=Browser("Br").Page("Page").ChildObjects(cc)
For i=lbound(collcc) to ubound(collcc)
Msgbox collcc(x).getroproperty("innertext")
x =x +9
Next
The problem is that the script stops at the beginning of the for, saying that there is a "wrong number of arguments or invalid property assignment ubound" (and the same happens with lbound.
What am I doing wrong?!
Just from memory, but i think ChildObjects does not return an array. Try with
for i = 0 to collcc.Count - 1
....
next
Child object is the collection of objects so you needs to loop through "for each " Snippet given below
for each col in collcc
Msgbox col.getroproperty("innertext")
Next
Thanks
Sai
Related
I have this code in VBS:
Dim Arg()
Set objArgs = WScript.Arguments
for i=0 to objArgs.Count
Arg(i) = Replace(objArgs(i),"\n",vbNewLine,1,-1,1)
... (yes, the for has a Next at the end)
(example arguments: "hello\nworld" "test" 0 64)
But when I run it, it throws an error: The subscript is out of range (line 4, column 3).
Am I incorrectly using the arrays, or is the problem in the for, or what is wrong?
Arrays in VBScript are zero ordinal based that means that if you have for example ten elements in the array they will be numbered zero to nine.
So when using Count it will return the number of elements not their position in the array so you will need to minus one from the Count or VBScript will report a "Subscript out of range" error as there is no 11th element in the array to iterate to.
As suggested in the comments, you want to do this;
For i = 0 To objArgs.Count - 1
The other issue is you declare a dynamic array (Dim Args()) but never initialise it before trying to insert elements into it. You could see this answer to a similar question that explains the problem. When using a dynamic array declaration you need to initialise it using ReDim.
Useful Links
subscript out of range while adding items to array
Visual Basic scripting dynamic array
I did research this question but could not find the specific answer I was looking for and am actually even more confused at present.
I created a macro that would run through rows on a sheet and run boolean checks on a number of cells in each row that looked for the presence or absence of specific values, or calculated the outcome of a specific inequality. On the basis of those checks, the macro may or may not pass the row number into a specific array. That part is working fine.
My issue is, now that I have the row numbers (stored in variant arrays) - I cannot figure out how to properly concatenate that data into a range and then take a bulk excel action on those items. What I'd like to do is create a range of those values and then delete all of those rows at once rather than looping through.
My macro is on my work computer, but here's something I wrote that should explain what I'm trying to do:
Sub Test()
Dim Str As String
Dim r As Range
Dim i, a As Integer
Dim Count As Integer
Dim RngArray()
Count = ThisWorkbook.Sheets("Sheet1").Cells(Rows.Count, "A:A").End(xlUp).Row
ReDim RngArray(Count)
a = 0
For i = 1 To Count
If Not i = Count Then
RngArray(a) = i
Str = Str & RngArray(a) & ":" & RngArray(a) & ", "
a = a + 1
ElseIf i = Count Then
RngArray(a) = i
Str = Str & RngArray(a) & ":" & RngArray(a)
a = a + 1
Else: End If
Next i
Set r = Range(Str)'Error Can Appear here depending on my concatenation technique
Range(Str).EntireRow.Delete 'error will always appear here
End Sub
I've combined a few steps here and left out any Boolean checks; in my actual macro the values in the arrays are already stored and I loop from LBound to UBound and concatenate those values into a string of the form ("1:1, 2:2, 3:3, ...., n:n")
The reason why I did this is that the rows are all over the sheet and I wanted to get to a point where I could pass the argument
Range("1:1, 2:2, 3:3, ..., n:n").EntireRow.Delete
I think it's clear that I'm just not understanding how to pass the correct information to the range object. When I try to run this I get a "Method Range of Object Global" error message.
My short term fix is to just loop through and clear the rows and then remove all of the blank rows (the macro keeps track of absolute positions of the rows, not the rows after an iterative delete) - but I'd like to figure out HOW to do this my way and why it's not working.
I'm open to other solutions as well, but I'd like to understand what I'm doing wrong here. I should also mention that I used the Join() to try to find a workaround and still received the same type of error.
Thank you.
After some experimentation with my dataset for the macro above, I discovered that it worked on small sets of data in A:A but not larger sets.
I ran Debug.Print Len(Str) while tweaking the set size and macro and found that it appears Range() can only accept a maximum of 240 characters. I still don't understand why this is or the reason for the specific error message I received, but the macro will work if Len(Str) < 240.
I'll have to loop backwards through my array to delete these rows if I want to use my present method...or I may just try something else.
Thanks to Andrew for his attention to this!
I have a dataset stored in SUBJ{s}.,and then fields SUBJ.WORDS{w} and SUBJ.RECALL{r}. I tried to create a loop that finds when SUBJ.RECALL corresponds to 1 (1=word remembered, 0 not remembered). After that I want to have displayed the words that correspond to the positions where SUBJ.RECALL is 1. Say
SUBJ{1}.WORDS{1}={‘Apple’, ‘Melon’, ‘Cheese’ ,’Pancakes’,Tomatoes’}% words presented.
`SUBJ{1}.RECALL{1}=[1 0 0 1 1]% 1=word recalled 0=word non recalled.
What I want is to display the words that have been recalled, meaning the words that correspond to 1 in SUBJ.RECALL.
I have done this:
for s=1:length(SUBJ)
for w=1:length(SUBJ.WORDS)
for r=1:length(SUBJ.RECALL)
if SUBJ{s}.RECALL{r}==1
disp(SUBJ{s}.WORDS{(SUBJ.RECALL{r}==1)})
end
end
end
end
Error: Attempt to reference field of non-structure array.
for s=1:length(SUBJ)
for w=1:length(SUBJ.WORDS)
for r=1:length(SUBJ.RECALL)
find(SUBJ{s}.RECALL{r}==1)
disp(SUBJ{s}.WORDS{(SUBJ.RECALL{r}==1)})
end
end
end
Error: Attempt to reference field of non-structure
Thanks in advance for any comment!
You probably do not need this many for-loops, as you can process the cell element contents using find. I included a sample code below. This works for your sample data, but might fail with whole dataset as i don't know the structure.
for s=1:length(SUBJ)
% Store in variables to make code more readable
words = SUBJ{s}.WORDS{1};
hits = SUBJ{s}.RECALL{1};
if max(hits) == 1 % Only print when hits
disp(words(find(hits)))
end
end
As of now, I'm sending only an empty array through the query-string.
selectPONumber=[]
Have no idea why I'm getting this error. The stacktrace points the Next on this.
If context.Request.QueryString("selectPONumber").Count <> 0 Then
For u = 1 To request.QueryString("selectPONumber").Count
selectPONumber.Add(request.QueryString("selectPONumber")(u))
Next
End If
How is it getting past the if if the .Count is 0? Is my query string formatting incorrect?
If it had values it would look like
selectPONumber=[value1, value2,...]
Many thanks in advance!
Extra Credit
Yes, vb.net did not read selectPONumber as an array when using []. All that's necessary is to to do selectPONumber=value1, value2,...
Thank-you very much for the above and beyond!
Are you saying your querystring looks like this?
mysite/mypage.aspx?selectPONumber=[]
If so, you are passing the string "[]" and Context.Request.QueryString("selectPONumber").Count == 2. It would evaluate to 0 for mysite/mypage.aspx?selectPONumber=.
Also, VB.NET arrays are zero-based. Use:
For u = 0 To request.QueryString("selectPONumber").Count-1
Hey i'm having problems creating a simple button for a programme which finds the largest word in an array and puts it into a textbox. I've done most of the coding (I hope) was wondering if somebody could help me actually with the code that finds the largest text in the array as I am struggling the most with that.
Private Sub btnLongName_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles btnLongName.Click
Dim LongName As String
Dim LengthOfLongestName As Integer
Dim UltimateName As String
For i As Integer = 0 To 5
LongName = Members(i).Name
LengthOfLongestName = Len(LongName)
If Members(i).Name.Length > LengthOfLongestName Then
End If
Next i
txtResult.Text = "The longest name is " & UltimateName & " ."
End Sub
End Class
Thanks for your time - its for college homework, struggling big time on it :(
edit: I've edited the code
Since this is homework, I won't write the code for you; instead I'll try to give you some hints that will point you in the right direction.
Declare a variable of an appropriate type to hold the <longest value so far>, initialize it with the "shortest" value for that type.
Loop through all the values in the array (perhaps with a For or For Each loop)
Pseudo-code for the inside your loop:
If the Length of <the value being checked> exceeds _
the Length of the <longest value so far> Then
Assign <the value being checked> to the <longest value so far>
End If
When the loop finishes, the <longest value so far> will be the longest value in the array.
Notes
You can use MSDN as a reference on how to use a For loop or a For Each loop (If you haven't learned For loops yet, you can also use a Do Loop)
<the value being checked> will be different on each iteration through the loop; it should correspond to each consecutive value in your array. You can verify that this is working by setting a breakpoint.
You can get the length of a string by saying myString.Length
If you've learned about Functions, consider writing a function that takes an array as a parameter, and returns the longest value in the array.
There are certainly ways you could do this with LINQ, but I don't think that is the goal of the assignment ;-]
In response to Edit 1:
Your If statement needs to be inside of some sort of loop (For, For Each, Do, etc) I think this is the key concept that you are missing.
Instead of comparing LongName.Length to LengthOfLongestName, you need to compare the length of an entry in your array to LengthOfLongestName
You're on the right track with Members(0).Name.Length, but you can't just check element 0; you have to check every element in the array.
Given your current code, you'll probably be assigning <An entry in your array>.Name to LongName
The last index in a one-dimensional array is <array>.Length - 1 or <array>.GetUpperBound(0).
The following doesn't really address anything in your assignment, but I hope it will give you some ideas on how to go through all the items in your list:
' A For loop that does a message box for each of the numbers from 0 to 5 '
For i as Integer = 0 To 5
MessageBox.Show(i)
Next i
' Code that does a message box with the names of the 2nd, 3rd and last '
' entries in Members '
' (Remember that the first item is at 0, the second item is at 1, etc...) '
MessageBox.Show(Members(1).Name)
MessageBox.Show(Members(2).Name)
MessageBox.Show(Members(Members.GetUpperBound()).Name)
In response to Edit 2:
You're getting warmer...
You should only update LongName and LengthOfLongName if the current value is the longest you've seen so far (i.e. they should be assigned inside of the If statement)
You have to go to the last index of the array, not 5. See above (the response to your first edit) on how to get that last index.
You don't really need the UltimateName variable; you can just use LongName ;-]
You might want to use <stringVariable>.Length instead of Len(<stringVariable>) to be consistent.
What you are missing is a loop that checks each member, and putting the If statement inside it and make it compare the length of the name to the longest name that you have found so far. If the name is longer, put it in the variable for the longest found, and update the length variable.
You can either initialise the variables with the name of the first member and loop from the second member and on, or you can initialise the variables with an empty string and loop all the members. Personally I prefer the latter one.