[lnkForumImage]
TotalShareware - Download Free Software

Confronta i prezzi di migliaia di prodotti.
Asp Forum
 Home | Login | Register | Search 


 

Saucer Man

11/26/2010 10:21:00 PM

How can I randomize the contents of a listview? Currently, the contents are
alphabetical by one of the sub-columns.

--
Thanks.


10 Answers

(nobody)

11/26/2010 11:42:00 PM

0

"Saucer Man" <saucerman@nospam.net> wrote in message
news:icpbt9$tpg$1@news.mixmin.net...
> How can I randomize the contents of a listview? Currently, the contents
> are alphabetical by one of the sub-columns.

If this is related to your previous request with filling the ListView with
file names, then this is not a good design. Imagine that you want to add a
right click menu later, if you change the position, then the user would be
confused about which file the menu would apply for. Perhaps if you explain
why you need to do this, someone would provide a better approach. If you
want to access the ListItems in a random fashion instead, then you could
use:

Randomize
r = Int(ListView1.ListItems.Count * Rnd) + 1
Debug.Print r, ListView1.ListItems(r).Text


Saucer Man

11/27/2010 4:03:00 PM

0

"Nobody" <nobody@nobody.com> wrote in message
news:icpglj$2hg$1@speranza.aioe.org...
> If this is related to your previous request with filling the ListView with
> file names, then this is not a good design. Imagine that you want to add a
> right click menu later, if you change the position, then the user would be
> confused about which file the menu would apply for. Perhaps if you explain
> why you need to do this, someone would provide a better approach. If you
> want to access the ListItems in a random fashion instead, then you could
> use:
>
> Randomize
> r = Int(ListView1.ListItems.Count * Rnd) + 1
> Debug.Print r, ListView1.ListItems(r).Text
>
>

I was looking to randomize the order of the list to "shuffle" the
arrangement. The listview is kind of a "playlist". I did what I needed to
do by using a simple shuffle array to export the list to a text file. Then
I clear the listview and import the text file back into it. It works but
seems like a round-about way of doing it.


(nobody)

11/27/2010 5:32:00 PM

0

"Saucer Man" <saucerman@nospam.net> wrote in message
news:icra47$u28$1@news.mixmin.net...
> I was looking to randomize the order of the list to "shuffle" the
> arrangement. The listview is kind of a "playlist". I did what I needed
> to do by using a simple shuffle array to export the list to a text file.
> Then I clear the listview and import the text file back into it. It works
> but seems like a round-about way of doing it.

You don't have to remove and add the list items, you can just swap the
contents. Example

s = ListView1.ListItems(a).Text
ListView1.ListItems(a).Text = ListView1.ListItems(b).Text
ListView1.ListItems(b).Text = s

Do the same with SubItems, example:

s = ListView1.ListItems(a).SubItems(1)
ListView1.ListItems(a).SubItems(1) = ListView1.ListItems(b).SubItems(1)
ListView1.ListItems(b).SubItems(1) = s

Instead of using Copy&Paste and listing all subitems, you can use a For loop
and loop through ListView1.ColumnHeaders.Count-1, to swap the subitems, just
in case you add more columns later. It would be better to put the whole
thing in a routine:

Private Sub SwapListItem(ByVal a As Long, ByVal b As Long)
' ToDo: Add code
End Sub


As for making a random list, you can use an array of Long, and generate
random numbers and check if they exist in the array, and if not, add them.
Another approach, is to add numbers to a Collection, which rejects duplicate
keys. Example:

Dim o As New Collection
Dim i As Long
Dim r As Long

On Error Resume Next ' Ignore error 457: The key is already...
Do While o.Count < ListView1.ListItems.Count
r = Int(ListView1.ListItems.Count * Rnd) + 1
o.Add r, Str(r)
Loop
On Error GoTo 0

For i = 1 To o.Count
Debug.Print o(i)
Next


Saucer Man

11/27/2010 6:44:00 PM

0

"Nobody" <nobody@nobody.com> wrote in message
news:icrfad$5k2$1@speranza.aioe.org...
> You don't have to remove and add the list items, you can just swap the
> contents. Example
>
> s = ListView1.ListItems(a).Text
> ListView1.ListItems(a).Text = ListView1.ListItems(b).Text
> ListView1.ListItems(b).Text = s
>
> Do the same with SubItems, example:
>
> s = ListView1.ListItems(a).SubItems(1)
> ListView1.ListItems(a).SubItems(1) = ListView1.ListItems(b).SubItems(1)
> ListView1.ListItems(b).SubItems(1) = s
>
> Instead of using Copy&Paste and listing all subitems, you can use a For
> loop and loop through ListView1.ColumnHeaders.Count-1, to swap the
> subitems, just in case you add more columns later. It would be better to
> put the whole thing in a routine:
>
> Private Sub SwapListItem(ByVal a As Long, ByVal b As Long)
> ' ToDo: Add code
> End Sub
>
>
> As for making a random list, you can use an array of Long, and generate
> random numbers and check if they exist in the array, and if not, add them.
> Another approach, is to add numbers to a Collection, which rejects
> duplicate keys. Example:
>
> Dim o As New Collection
> Dim i As Long
> Dim r As Long
>
> On Error Resume Next ' Ignore error 457: The key is already...
> Do While o.Count < ListView1.ListItems.Count
> r = Int(ListView1.ListItems.Count * Rnd) + 1
> o.Add r, Str(r)
> Loop
> On Error GoTo 0
>
> For i = 1 To o.Count
> Debug.Print o(i)
> Next
>

Here is what I am doing...

'Populate array with numbers 1 thru total.
For pLoop = 1 To lngTotal
MyArray(pLoop) = pLoop
Next pLoop

'Shuffle array and create main list.
Open App.Path & "\list.txt" For Output As #1

For sLoop = lngTotal To 1 Step -1
rNumb = Int((Rnd * lngTotal) + 1)
Hld = MyArray(rNumb)
MyArray(rNumb) = MyArray(sLoop)
MyArray(sLoop) = Hld
Write #1, lv1.ListItems(MyArray(sLoop));
lv1.ListItems(MyArray(sLoop)).SubItems(1);
lv1.ListItems(MyArray(sLoop)).SubItems(2)
Next sLoop

Close #1

....but I think something is wrong. If I look at the list.txt file after
this is finished, I can't find some of the items that I know were in the
listview. The items are shuffled and it appears that the same amount of
items are in the list.txt file as the listview but some are missing. I
don't know if it is listing some more than once. Is there something wrong
with this code that you can see? It is a little confusing to me but am I
writing the wrong variable to the file?


(nobody)

11/27/2010 8:20:00 PM

0

"Saucer Man" <saucerman@nospam.net> wrote in message
news:icrjhv$7rk$1@news.mixmin.net...
> Here is what I am doing...
>
> 'Populate array with numbers 1 thru total.
> For pLoop = 1 To lngTotal
> MyArray(pLoop) = pLoop
> Next pLoop
>
> 'Shuffle array and create main list.
> Open App.Path & "\list.txt" For Output As #1
>
> For sLoop = lngTotal To 1 Step -1
> rNumb = Int((Rnd * lngTotal) + 1)
> Hld = MyArray(rNumb)
> MyArray(rNumb) = MyArray(sLoop)
> MyArray(sLoop) = Hld
> Write #1, lv1.ListItems(MyArray(sLoop));
> lv1.ListItems(MyArray(sLoop)).SubItems(1);
> lv1.ListItems(MyArray(sLoop)).SubItems(2)
> Next sLoop
>
> Close #1
>
> ...but I think something is wrong. If I look at the list.txt file after
> this is finished, I can't find some of the items that I know were in the
> listview. The items are shuffled and it appears that the same amount of
> items are in the list.txt file as the listview but some are missing. I
> don't know if it is listing some more than once. Is there something wrong
> with this code that you can see? It is a little confusing to me but am I
> writing the wrong variable to the file?

That's normal. Random values may include duplicate values, so you are not
seeing the whole list. See my previous reply.

Also, there are few locations that you can save files to without running
into permission errors if the user happened to be a member of the limited
"Users" group. App.Path is usually not of them. You are not getting errors
now because you are probably running as Administrator. The places that you
can save to are the user's Temp folder, CSIDL_APPDATA, and
CSIDL_LOCAL_APPDATA. Search the newsgroups for
GetTempPath/SHGetFolderPath/SHGetSpecialFolderLocation to see how to get
these paths, or drop the file method all together.



Saucer Man

11/27/2010 9:08:00 PM

0

"Nobody" <nobody@nobody.com> wrote in message
news:icrp5j$v8p$1@speranza.aioe.org...
> That's normal. Random values may include duplicate values, so you are not
> seeing the whole list. See my previous reply.
>
> Also, there are few locations that you can save files to without running
> into permission errors if the user happened to be a member of the limited
> "Users" group. App.Path is usually not of them. You are not getting errors
> now because you are probably running as Administrator. The places that you
> can save to are the user's Temp folder, CSIDL_APPDATA, and
> CSIDL_LOCAL_APPDATA. Search the newsgroups for
> GetTempPath/SHGetFolderPath/SHGetSpecialFolderLocation to see how to get
> these paths, or drop the file method all together.
>
I started using the Collection method you mentioned earlier. I don't
understand it but it is working without duplicates and it is very minimal
code. How is this Collection different from an Array?


Larry Serflaten

11/29/2010 2:35:00 AM

0


"Saucer Man" <saucerman@nospam.net> wrote

> 'Shuffle array and create main list.
> Open App.Path & "\list.txt" For Output As #1
>
> For sLoop = lngTotal To 1 Step -1
> rNumb = Int((Rnd * lngTotal) + 1)
> Hld = MyArray(rNumb)
> MyArray(rNumb) = MyArray(sLoop)
> MyArray(sLoop) = Hld
> Write #1, lv1.ListItems(MyArray(sLoop));
> lv1.ListItems(MyArray(sLoop)).SubItems(1);
> lv1.ListItems(MyArray(sLoop)).SubItems(2)
> Next sLoop
>
> Close #1
>
> ...but I think something is wrong.

Move the Write command out of the shuffle loop and into a loop of its own.
During the shuffle you may swap items that were already swapped, and can
end up writing the same items to the disk.

If you move the Write command out of the loop, it won't matter if you
swap items more than once, in the end there will be a shuffled array, and
that is what you use to write to the file.

LFS


DaveO

11/29/2010 9:41:00 AM

0

Hi

Another method to randomly "sort" the content of a listview, first shuffle a
list of numbers equal to the quantity of items in the listview, then add
theem to a new zero width column to the listview then sort on that column
then delete the column - much faster than all that mucking about swapping
items - You don't even have to bother to pad the numbers with leading zeros
because you want a random order so 1,10,11,12,2,3,4,5,6,7,8,9 is fine for 1
to 12.

Here is a simple fast shuffle routine you can easily adapt:
Dim a(20) As Integer
Dim i As Integer
Dim x As Integer
Dim s As Integer

Randomize

For i = 0 To 20
a(i) = i
Next

For i = 20 To 1 Step -1
x = Int(Rnd(1) * i)
s = a(i)
a(i) = a(x)
a(x) = s
Next

For i = 0 To 20
Debug.Print i, a(i)
Next

Dave O.

"Saucer Man" <saucerman@nospam.net> wrote in message
news:icpbt9$tpg$1@news.mixmin.net...
> How can I randomize the contents of a listview? Currently, the contents
> are alphabetical by one of the sub-columns.
>
> --
> Thanks.
>


(nobody)

11/29/2010 3:46:00 PM

0

"Nobody" <nobody@nobody.com> wrote in message
news:icrp5j$v8p$1@speranza.aioe.org...
> "Saucer Man" <saucerman@nospam.net> wrote in message
> news:icrjhv$7rk$1@news.mixmin.net...
>> Here is what I am doing...
>>
>> 'Populate array with numbers 1 thru total.
>> For pLoop = 1 To lngTotal
>> MyArray(pLoop) = pLoop
>> Next pLoop
>>
>> 'Shuffle array and create main list.
>> Open App.Path & "\list.txt" For Output As #1
>>
>> For sLoop = lngTotal To 1 Step -1
>> rNumb = Int((Rnd * lngTotal) + 1)
>> Hld = MyArray(rNumb)
>> MyArray(rNumb) = MyArray(sLoop)
>> MyArray(sLoop) = Hld
>> Write #1, lv1.ListItems(MyArray(sLoop));
>> lv1.ListItems(MyArray(sLoop)).SubItems(1);
>> lv1.ListItems(MyArray(sLoop)).SubItems(2)
>> Next sLoop
>>
>> Close #1
>>
>> ...but I think something is wrong. If I look at the list.txt file after
>> this is finished, I can't find some of the items that I know were in the
>> listview. The items are shuffled and it appears that the same amount of
>> items are in the list.txt file as the listview but some are missing. I
>> don't know if it is listing some more than once. Is there something
>> wrong with this code that you can see? It is a little confusing to me
>> but am I writing the wrong variable to the file?
>
> That's normal. Random values may include duplicate values, so you are not
> seeing the whole list. See my previous reply.

Somehow I missed that you are actually swapping the items, but like Larry
said, the problem is that you have the write within the loop.

Also, the loop variable name is confusing. Starting it with "s" usually
indicates that it's of type String. See "Constant and Variable Naming
Conventions" and "Object Naming Conventions" in MSDN. See also these pages:

INFO: Microsoft Consulting Services Naming Conventions for Visual Basic
http://support.microsoft.com/default.aspx?scid=kb;en...

http://en.wikipedia.org/wiki/Hungaria...



Saucer Man

11/29/2010 9:43:00 PM

0

"Nobody" <nobody@nobody.com> wrote in message
news:id0hso$fi8$1@speranza.aioe.org...
> "Nobody" <nobody@nobody.com> wrote in message
> news:icrp5j$v8p$1@speranza.aioe.org...
> Somehow I missed that you are actually swapping the items, but like Larry
> said, the problem is that you have the write within the loop.
>
> Also, the loop variable name is confusing. Starting it with "s" usually
> indicates that it's of type String. See "Constant and Variable Naming
> Conventions" and "Object Naming Conventions" in MSDN. See also these
> pages:
>
> INFO: Microsoft Consulting Services Naming Conventions for Visual Basic
> http://support.microsoft.com/default.aspx?scid=kb;en...
>
> http://en.wikipedia.org/wiki/Hungaria...
>
>

Ahh...ok. So it was the write in the loop. Good to know. Thanks Larry. I
think I am having success with the collections method. I replaced the
debug.print with the write and it appears to work great. Thanks Nobody.

Thanks Dave for the suggestion about the additional column in the listview.
I didn't think of that although I do use hidden columns in other listviews
for other purposes. It could have worked here equally well.

Thanks again everyone!