Hello and welcome to our community! Is this your first visit?
Register
Enjoy an ad free experience by logging in. Not a member yet? Register.
Page 1 of 2 12 LastLast
Results 1 to 15 of 25
  1. #1
    New to the CF scene
    Join Date
    May 2013
    Posts
    5
    Thanks
    7
    Thanked 0 Times in 0 Posts

    Random image script that ALLOWS duplicates?

    I am looking for code for a random image script that will display XX number of images at random from a directory. AND I want to ALLOW duplicates.

    So an array that is generated where there is duplication is required, as the grid of images (144) is more than the number of images in the directory (78).

    Many thanks if anyone has info!
    Mike

  • #2
    Supreme Master coder! Philip M's Avatar
    Join Date
    Jun 2002
    Location
    London, England
    Posts
    17,734
    Thanks
    202
    Thanked 2,508 Times in 2,486 Posts
    Code:
    <script type = "text/javascript">
    
    var result = [];
    var num = 78;
    var grid = 144;
    for (var i = 0; i<grid; i++) {
    result[i] = Math.floor(Math.random() * num +1);  // generates 1-78 randomly 144 times
    }
    alert (result);  // for testing
    
    </script>
    Of course, it is possible that some numbers in the range 1-78 will not be generated at all, and it is also possible that the same number occurs twice (or even more) in succession.

    Quizmaster: The Goethe Institute in London promotes the culture of which country?
    Contestant: Nepal.

    All the code given in this post has been tested and is intended to address the question asked.
    Unless stated otherwise it is not just a demonstration.

  • Users who have thanked Philip M for this post:

    palouseflyer (05-30-2013)

  • #3
    Senior Coder jmrker's Avatar
    Join Date
    Aug 2006
    Location
    FL
    Posts
    3,032
    Thanks
    36
    Thanked 495 Times in 489 Posts

    Lightbulb

    Two more alternate solutions:
    1st is 'Philip M's, which may allow 2 or more duplicates.

    2nd method allows one duplicate in any group provided grid is < (2 * num).

    3rd method is also limited to one duplicate so long as num is multiple of grid

    All methods can be adjusted for any amount of num and grid values,
    but 2nd and 3rd allow for limited number of duplicated values.

    There are probably more ways to skin this cat!!!

    Code:
    <!DOCTYPE HTML>
    <html>
    <head>
    <title> Untitled </title>
    <meta charset="utf-8">
    
    <style type="text/css">
    #dbug1, #dbug2, #dbug3 { height:150px; width:400px; border:1px solid red; }
    </style>
    
    </head>
    <body>
    Method 1<br><div id="dbug1"></div>
    <hr>
    Method 2<br><div id="dbug2"></div>
    <hr>
    Method 3<br><div id="dbug3"></div>
    
    <script type = "text/javascript">
    // Modified from: http://www.codingforums.com/showthread.php?t=296120
    
    var num = 78;  var grid = 144;  // used as global for testing purposes only
    
    function Method1(IDS) {
      var result1 = [];
      for (var i = 0; i<grid; i++) {
        result1[i] = Math.floor(Math.random() * num +1);  // generates 1-78 randomly 144 times
      }
      show(IDS,result1);
    }
    
    function Method2(IDS) {
      var result2 = [];
      for (var i=0; i<num; i++) { result2.push(i+1); }
      result2 = result2.concat(result2);  // 'concat' more if needed past 156
      result2 = result2.slice(0,grid);
      result2 = result2.sort(randOrd);
      show(IDS,result2);
    }
    
    function Method3(IDS) {
      var result3 = [];
      for (var i=0; i<grid; i++) { result3.push((i%num)+1); }
      result3 = result3.sort(randOrd);
      show(IDS,result3);
    }
    
    window.onload = function() {
      Method1('dbug1');
      Method2('dbug2');
      Method3('dbug3');
    }
    
    function randOrd() {
      return (Math.round(Math.random())-0.5);
    }
    function show(IDS,rarray) {
      document.getElementById(IDS).innerHTML = rarray.join(' ');
    }
    </script>
    
    </body>
    </html>

  • Users who have thanked jmrker for this post:

    palouseflyer (05-30-2013)

  • #4
    Supreme Master coder! Old Pedant's Avatar
    Join Date
    Feb 2009
    Posts
    25,020
    Thanks
    75
    Thanked 4,323 Times in 4,289 Posts
    Quote Originally Posted by palouseflyer View Post
    I am looking for code for a random image script that will display XX number of images at random from a directory.
    One *VERY* important note here:

    JavaScript has *NO ABILITY* to find out *WHAT* images are in a directory.

    So unless your images are named/numbered in some regular pattern (e.g., "img0.jpg", "img1.jpg", ..., "img78.jpg") none of the advice you have been given is going to work.

    If the images have "natural" names (e.g., "john_age15.png", "lincoln_memoriial_at_sunset.jpg", etc.) then you will need to either create a list of those names as an array in JS or use server side code to do what you are after.
    An optimist sees the glass as half full.
    A pessimist sees the glass as half empty.
    A realist drinks it no matter how much there is.

  • Users who have thanked Old Pedant for this post:

    palouseflyer (05-30-2013)

  • #5
    Senior Coder jmrker's Avatar
    Join Date
    Aug 2006
    Location
    FL
    Posts
    3,032
    Thanks
    36
    Thanked 495 Times in 489 Posts
    Old Pedant's advise is true.

    I AssUMe_d your picture names were already collected from the directory and in an array that could be indexed.
    The 'result' array was a suffix to the common filename or an index pointer into the saved array.

    The 78 images can be collected easily on a server using: ls -1 > dirList.txt
    to create a text file which could be read by an ajax function.

    OR you could convert the dirList.txt file to an external JS file and index into that with the functions provided.

  • Users who have thanked jmrker for this post:

    palouseflyer (05-31-2013)

  • #6
    Supreme Master coder! Old Pedant's Avatar
    Join Date
    Feb 2009
    Posts
    25,020
    Thanks
    75
    Thanked 4,323 Times in 4,289 Posts
    Quote Originally Posted by jmrker View Post
    The 78 images can be collected easily on a server using: ls -1 > dirList.txt
    Ummm...that command would only work on linux/unix servers.

    For Windows, the corresponding command is dir /B > dirList.txt
    An optimist sees the glass as half full.
    A pessimist sees the glass as half empty.
    A realist drinks it no matter how much there is.

  • #7
    New to the CF scene
    Join Date
    May 2013
    Posts
    5
    Thanks
    7
    Thanked 0 Times in 0 Posts
    Dear Philip M, jmrkr, Old Pedant

    THANK YOU so much for your help!

    This is exactly what I am looking for!

    I think Philip M's method (Method 1) is perfect as I do not care how many times we may see a duplicate in the array.

    2 follow up questions:

    1. How to generate a 12 x 12 grid?

    2. How to add (document.write?) to include the path to the image so the page renders the image itself?


    I will have one directory of the 78 images named in sequence:

    img01.JPG
    img02.JPG
    img03.JPP

    img78.JPG

    And I need the page to render as below as a 12 x 12 grid. As shown here:


    THANKS so much I really appreciate the help. I have been doing experiments with image patterns received from a symbol set I created as shown below. I have been drawing these by hand and want to build a simple web page that can create these automatically (and save me some time!)

    Here is an example of a 12 x 12 grid showing the images (each image is a 9x9 symbol pattern):


    ***

    Quote Originally Posted by jmrker View Post
    Two more alternate solutions:
    1st is 'Philip M's, which may allow 2 or more duplicates.

    2nd method allows one duplicate in any group provided grid is < (2 * num).

    3rd method is also limited to one duplicate so long as num is multiple of grid

    All methods can be adjusted for any amount of num and grid values,
    but 2nd and 3rd allow for limited number of duplicated values.

    There are probably more ways to skin this cat!!!

    Code:
    <!DOCTYPE HTML>
    <html>
    <head>
    <title> Untitled </title>
    <meta charset="utf-8">
    
    <style type="text/css">
    #dbug1, #dbug2, #dbug3 { height:150px; width:400px; border:1px solid red; }
    </style>
    
    </head>
    <body>
    Method 1<br><div id="dbug1"></div>
    <hr>
    Method 2<br><div id="dbug2"></div>
    <hr>
    Method 3<br><div id="dbug3"></div>
    
    <script type = "text/javascript">
    // Modified from: http://www.codingforums.com/showthread.php?t=296120
    
    var num = 78;  var grid = 144;  // used as global for testing purposes only
    
    function Method1(IDS) {
      var result1 = [];
      for (var i = 0; i<grid; i++) {
        result1[i] = Math.floor(Math.random() * num +1);  // generates 1-78 randomly 144 times
      }
      show(IDS,result1);
    }
    
    function Method2(IDS) {
      var result2 = [];
      for (var i=0; i<num; i++) { result2.push(i+1); }
      result2 = result2.concat(result2);  // 'concat' more if needed past 156
      result2 = result2.slice(0,grid);
      result2 = result2.sort(randOrd);
      show(IDS,result2);
    }
    
    function Method3(IDS) {
      var result3 = [];
      for (var i=0; i<grid; i++) { result3.push((i%num)+1); }
      result3 = result3.sort(randOrd);
      show(IDS,result3);
    }
    
    window.onload = function() {
      Method1('dbug1');
      Method2('dbug2');
      Method3('dbug3');
    }
    
    function randOrd() {
      return (Math.round(Math.random())-0.5);
    }
    function show(IDS,rarray) {
      document.getElementById(IDS).innerHTML = rarray.join(' ');
    }
    </script>
    
    </body>
    </html>

  • #8
    Senior Coder jmrker's Avatar
    Join Date
    Aug 2006
    Location
    FL
    Posts
    3,032
    Thanks
    36
    Thanked 495 Times in 489 Posts

    Arrow

    Quote Originally Posted by Old Pedant View Post
    Ummm...that command would only work on linux/unix servers.

    For Windows, the corresponding command is dir /B > dirList.txt
    Yes, but I'm on a university server so I only use the MS command when I'm running locally on my desktop computer.

    There I go, AssUMe_ing again!

  • Users who have thanked jmrker for this post:

    palouseflyer (05-31-2013)

  • #9
    New to the CF scene
    Join Date
    May 2013
    Posts
    5
    Thanks
    7
    Thanked 0 Times in 0 Posts
    Yippie
    I finally got this working! Thanks jmrkr and everyone for all of your help!!
    Mike

    Quote Originally Posted by jmrker View Post
    Old Pedant's advise is true.

    I AssUMe_d your picture names were already collected from the directory and in an array that could be indexed.
    The 'result' array was a suffix to the common filename or an index pointer into the saved array.

    The 78 images can be collected easily on a server using: ls -1 > dirList.txt
    to create a text file which could be read by an ajax function.

    OR you could convert the dirList.txt file to an external JS file and index into that with the functions provided.

  • #10
    Supreme Master coder! Philip M's Avatar
    Join Date
    Jun 2002
    Location
    London, England
    Posts
    17,734
    Thanks
    202
    Thanked 2,508 Times in 2,486 Posts
    @jmrker -

    I think there is something wrong with your code as every time I test I get a very non-random sequence of numbers at the end:-

    Examples:-
    57 58 59 60 63 64
    59 60 61 62 65 66
    49 50 51 55 64 66
    56 57 59 61 65 66
    56 59 61 63 64 66
    60 61 62 63 64 65

    I think it lies in your randord() function which is biased.

    I think that it would be best (if the OP requires no more than one duplicate of each image - which he does not) to generate 1-78 twice in an array of 156, shuffle the whole array and take the first 144 values.

    Code:
    <script type = "text/javascript">
    
    Array.prototype.shuffle = function() {
    var s = [];
    while (this.length) s.push(this.splice(Math.random() * this.length, 1));
    while (s.length) this.push(s.pop());
    return this;
    }
    
    var myarray = [];
    var result = [];
    var num = 78;
    var grid = 144;  // not used
    for (var i =1; i<=num; i++) {
    myarray[i-1] = i;
    }
    for (var i = num; i < (num *2-1); i++) {
    myarray[i-1] = i-77;
    }
    alert (myarray);  // for testing
    
    result = myarray.shuffle();
    alert (result);
    
    </script>
    Last edited by Philip M; 05-31-2013 at 09:30 AM.

    All the code given in this post has been tested and is intended to address the question asked.
    Unless stated otherwise it is not just a demonstration.

  • #11
    Senior Coder jmrker's Avatar
    Join Date
    Aug 2006
    Location
    FL
    Posts
    3,032
    Thanks
    36
    Thanked 495 Times in 489 Posts

    Lightbulb

    Quote Originally Posted by Philip M View Post
    @jmrker -

    I think there is something wrong with your code as every time I test I get a very non-random sequence of numbers at the end:-

    Examples:-
    57 58 59 60 63 64
    59 60 61 62 65 66
    49 50 51 55 64 66
    56 57 59 61 65 66
    56 59 61 63 64 66
    60 61 62 63 64 65

    I think it lies in your randord() function which is biased.
    It might be that you are calling the wrong function.
    It is "randOrd()" not "randord()"

    If that's not it, let's see the code you are actually using.

  • #12
    Supreme Master coder! Philip M's Avatar
    Join Date
    Jun 2002
    Location
    London, England
    Posts
    17,734
    Thanks
    202
    Thanked 2,508 Times in 2,486 Posts
    Quote Originally Posted by jmrker View Post
    It might be that you are calling the wrong function.
    It is "randOrd()" not "randord()"

    If that's not it, let's see the code you are actually using.
    The code I am using is that which you posted in post #3. Copied and pasted without alteration.

    Yes, randOrd(). But as I say, copied and pasted.

    Final 6 numbers obtained from Method 2 in tests 1 minute ago

    58 59 62 63 64 65
    56 58 61 64 65 66
    60 61 62 63 64 65
    65 55 57 58 61 66
    58 59 61 62 65 66

    ... you must get the same sort of values. Method 3 gives similar results.
    Last edited by Philip M; 05-31-2013 at 04:06 PM.

    All the code given in this post has been tested and is intended to address the question asked.
    Unless stated otherwise it is not just a demonstration.

  • #13
    Senior Coder jmrker's Avatar
    Join Date
    Aug 2006
    Location
    FL
    Posts
    3,032
    Thanks
    36
    Thanked 495 Times in 489 Posts

    Question

    Quote Originally Posted by Philip M View Post
    The code I am using is that which you posted in post #3. Copied and pasted without alteration.

    Yes, randOrd(). But as I say, copied and pasted.

    Final 6 numbers obtained from Method 2 in tests 1 minute ago

    58 59 62 63 64 65
    56 58 61 64 65 66
    60 61 62 63 64 65
    65 55 57 58 61 66
    58 59 61 62 65 66

    ... you must get the same sort of values. Method 3 gives similar results.
    I'm not sure what the problem is.

    I'm using an iMac at work running FF and a PC and FF at home where the test code was developed. Are you using a different browser?

    Here is a sample of the output I get when I just copied and pasted as you did. I'm not seeing any pattern sequence or repeats between methods.

    Method 1
    24 24 61 65 22 27 21 23 76 50 66 54 15 56 61 50 3 11 12 55 15 19 42 52 39 58 55 44 10 10 69 12 65 13 68 11 3 9 4 76 15 6 54 33 20 37 34 51 55 58 78 49 12 12 58 67 72 39 6 49 36 56 4 63 15 44 40 7 41 32 26 42 33 75 40 64 37 58 8 8 39 47 70 24 31 16 7 34 44 74 24 42 4 12 23 36 43 50 54 31 41 77 64 37 77 1 63 27 5 72 78 1 63 35 33 12 61 26 13 63 51 78 39 70 12 18 68 29 8 54 35 37 32 28 24 30 48 32 24 30 20 12 31 3
    Method 2
    1 43 2 3 6 44 4 29 5 11 10 12 9 45 7 8 19 46 28 14 18 38 37 17 16 13 20 21 15 30 39 23 47 24 26 48 22 25 27 42 41 40 34 33 35 31 32 36 52 53 54 9 50 49 51 56 55 2 8 7 10 58 57 1 12 11 59 77 60 14 13 61 62 63 15 3 66 64 17 65 74 70 69 67 71 4 16 5 6 18 73 75 76 68 72 78 22 19 20 23 21 24 25 27 26 29 30 28 35 37 33 34 31 40 41 32 36 42 38 39 49 44 50 59 60 43 56 58 51 45 55 53 52 57 54 46 48 61 47 62 65 66 63 64
    Method 3
    26 30 5 9 47 23 46 50 34 49 1 35 22 29 24 4 2 51 54 48 44 32 6 3 9 20 52 7 8 21 11 36 43 12 10 17 13 18 53 33 60 45 56 16 7 31 14 15 51 8 19 39 38 21 75 52 49 73 50 54 55 11 37 53 19 41 28 57 24 42 55 56 10 20 74 59 23 59 22 58 25 78 25 60 29 77 12 28 27 27 40 30 15 57 63 62 61 64 66 26 65 32 58 33 62 14 31 69 63 34 36 35 68 67 38 13 40 16 37 39 41 76 42 1 44 71 61 43 45 46 2 70 47 48 3 72 4 18 66 65 64 17 5 6
    It does not matter to me which version the OP uses.

    I do think it is interesting that we are not getting similar random results, but I cannot explain nor replicate the sequential patterns you seem to be getting when we run the same code ???
    I don't expect the random numbers to be the same, but I also don't expect any series to be displayed either.

  • #14
    Supreme Master coder! Old Pedant's Avatar
    Join Date
    Feb 2009
    Posts
    25,020
    Thanks
    75
    Thanked 4,323 Times in 4,289 Posts
    It can easily be shown that, mathematically, this is a lousy way to do a random ordering:
    Code:
    function randOrd() {
      return (Math.round(Math.random())-0.5);
    }
    result2 = result2.sort(randOrd);
    Some have noted that you get slightly better results using 0.6 or even 0.7 in place of 0.5, but it's still not a good way to shuffle an array. (It does depend somewhat on the internal sort algorithm used, of course. Heap sort is especially susceptible, for example.)

    A better way:
    Code:
    function shuffle( arr )
    {
        var out = [ ];
        for ( var n = arr.length; n > 0; --n )
        {
            var pick = Math.floor( Math.random() * n );
            out.push( arr[pick] );
            arr[pick] = arr[n-1];
        }
        return out;
    }
    But since he says he truly doesn't care how many times any given element is picked, I don't see any reason at all to use a shuffle. I'd stick with method 1.
    An optimist sees the glass as half full.
    A pessimist sees the glass as half empty.
    A realist drinks it no matter how much there is.

  • #15
    Senior Coder jmrker's Avatar
    Join Date
    Aug 2006
    Location
    FL
    Posts
    3,032
    Thanks
    36
    Thanked 495 Times in 489 Posts

    Lightbulb

    The following piece of code is an example that 'Old Pedant's shuffle() code is superior to the randOrd() function. What the second line of each block displays is the frequency of the suffled or randomized array when the position and value of the array are unchanged. If you run it 50 - 100 times, you will see the counts increase faster with the randOrd() function, indicating that the randomizing is biased, especially at the limits of the arrays.

    A graphical representation of the frequency counts would show a more level bar graph indicating that the values for the shuffle() function would be moved with better distribution.

    Code:
    <!DOCTYPE html>
    <html lang="en">
    <head>
    <meta charset="UTF-8" />
    <script type="text/javascript">
    function shuffle( arr ) {
        var out = [ ];
        for ( var n = arr.length; n > 0; --n )     {
            var pick = Math.floor( Math.random() * n );
            out.push( arr[pick] );
            arr[pick] = arr[n-1];
        }
        return out;
    }
    
    function randOrd() { return (Math.round(Math.random())-0.5); }
    
    </script>
    
    <style type="text/css">
    #debug1, #debug2, #debug3 { border:1px solid red; width:50%; }
    </style>
    
    <title> Untitled </title>
    
    </head>
    <body>
    Run count: <button id="btn" onclick="test()">0</button> <p>
    Shuffle<br>
    <div id="debug1"></div><p>
    Randomize<br>
    <div id="debug2"></div><p>
    Original<br>
    <div id="debug3"></div><p>
    
    <script type="text/javascript">
    var count = 0;
    var stat1 = zeroArray(25);
    var stat2 = zeroArray(25);
    function zeroArray(sz) { var out = [];  for (var i=0; i<sz; i++) { out.push(0); } return out; }
    function makeArray(sz) { var out = [];  for (var i=0; i<sz; i++) { out.push(i); } return out; }
    function statArray(arr,carr) {
      for (var i=0; i<arr.length; i++) { if (arr[i] == i) { carr[i]++; } }
    }
    function test() {
      var result1 = shuffle(makeArray(25));
      statArray(result1,stat1);
      document.getElementById('debug1').innerHTML
        = result1.join(' ')+'<br>Position unchanged: '+stat1.join(' ');
    
      var result2 = makeArray(25).sort(randOrd);
      statArray(result2,stat2);
      document.getElementById('debug2').innerHTML
        = result2.join(' ')+'<br>Position unchanged: '+stat2.join(' ');
    
      var result3 = makeArray(25);
      document.getElementById('debug3').innerHTML 
        = result3.join(' ')+'<br>'+zeroArray(25).join(' ');
     
      count++; document.getElementById('btn').innerHTML = count;
    }
    </script>
    
    </body>
    </html>
    The display for the randOrd() function does not change much with values of 0.5, 0.6 or 0.7

  • Users who have thanked jmrker for this post:

    Old Pedant (06-04-2013)


  •  
    Page 1 of 2 12 LastLast

    Tags for this Thread

    Posting Permissions

    • You may not post new threads
    • You may not post replies
    • You may not post attachments
    • You may not edit your posts
    •