Thread: Random Question Assign Program

  1. #1
    Registered User
    Join Date
    Oct 2005
    Posts
    30

    Random Question Assign Program

    Hello, Everyone:

    Today, I am trying to program in C++ which helps me assign hypothetically to each students from 50 questions. Unfortunately, when I wrote the program I am getting that some students have the same question number assign as other students and a few have the same question assign twice. Can you help me figure out what I did wrong in my program and how can I fix the program so each student has a unique question.

    Here is the program:
    Code:
    #include<iostream>
    
    using std::cout;
    using std::ios;
    
    #include<iomanip>
    
    using std::setw;
    using std::setprecision;
    using std::setiosflags;
    
    #include<cstdlib>
    #include<ctime>
    
    int main()
    {
    
        srand( time( 0 ) );
        int a[10][5], i , j;
            cout << setw(8);
        for( i = 1; i <=10; i++)
        {
           for( j = 1; j <=5; j++)
           {
              a[i][j] = 1 + rand() % 50;
               cout << a[i][j] << setw(8);
           }
        cout << '\n';
        }
    
    return 0;
    }
    
    <pegasus> g++ duplicates.cpp
    <pegasus> a.out
          35      13      26      39      25
          30       5      37      22       5
          18      33      21      15      47
          42      37      34      18      43
           3      42      45      16       1
          10       6      29      22      24
          31      39      13       9       8
           6       5       6       3      48
          24      15      17      23       4
          40      36      20      26      10
    <pegasus>
    I will appreciate any help from some one.
    Sincerely,
    Mike

  2. #2
    Registered User
    Join Date
    Jan 2005
    Posts
    7,366
    You should have an array of the 50 questions (or numbers corresponding to questions), then shuffle the array. Once the array is shuffled, you can walk through the array assigning each value to the next student.

    The best way to shuffle the array is to use random_shuffle from <algorithm>. You could write your own method, but be careful, it is easy to end up a little bit off and one student won't get a very random question. The basic idea is to start at the end, get a random value from 0 to that index, and then swap values with the element at the position of the random number. Repeat with the next to last index, and continue, decreasing the index until you get to the front of the array.

  3. #3
    Registered User
    Join Date
    Oct 2005
    Posts
    30
    Hello,

    I understand I have to use arrays in this program to get the random questions to eaach student. However, I have no idea where to input the

    Code:
    random_shuffle from <algorithm>
    Moreover, I really need advice as how to write the code. For example, clues which can help me understand better what I'm trying to do.

    Thank you for your time for some who can help me figure out how to write the code which can lead me to the solution.

  4. #4
    Registered User
    Join Date
    Jan 2005
    Posts
    7,366
    If you don't know about random_shuffle or aren't allowed to use it, just implement the "basic idea" that I described in my previous post.

  5. #5
    Cheesy Poofs! PJYelton's Avatar
    Join Date
    Sep 2002
    Location
    Boulder
    Posts
    1,728
    If you don't want to use random_shuffle, heres an easy way to create your own shuffle routine. Say you have an array where each value in the array equals it's index, for example a[0]=0, a[32]=32 etc. To shuffle this array simply do this:
    Code:
    for (int i=0; i<arraysize; i++)
         swap (a[i], a[rand()%arraysize]);  // or implement your own swapping code here
    
    for (int i=0; i<arraysize; i++)
         cout<<a[i]<<endl;
    
    // this will print out the numbers 0-arraysize in random order with NO repeats
    Once you understand how this works, its real easy to implement into your question program.

  6. #6
    Registered User
    Join Date
    Jan 2005
    Posts
    7,366
    As I said earlier, it is easy to be a little bit off when trying to write your own shuffle. The distribution has a significant and repeatable skew when using PJYelton's formula above.

    Try running this code and look at the distribution for index 0. Notice how b and c are consistently higher than a, x and y. You can change choice to 2 or 3 to use a better shuffle algorithm that makes the frequencies much closer together.
    Code:
    #include <iostream>
    #include <algorithm>
    #include <vector>
    #include <map>
    #include <cstdlib>
    #include <ctime>
    
    void BadShuffle(char a[], int size)
    {
        for (int i=0; i<size; i++)
            std::swap(a[i], a[std::rand()%size]);
    }
    
    void GoodShuffle(char a[], int size)
    {
        for (int i=size; i>0; --i)
            std::swap(a[i-1], a[std::rand()%i]);
    }
    
    void BuiltInShuffle(char a[], int size)
    {
        std::random_shuffle(a, a + size);
    }
    
    void OutputFreq(const std::vector<std::map<char, int> >&, int);
    
    int main()
    {
        std::srand(static_cast<unsigned>(std::time(0)));
    
        // BadShuffle = 1
        // GoodShuffle = 2
        // BuiltInShuffle = 3
        int choice = 1;
    
        const int arraysize = 25;
        char a[arraysize];
    
        std::vector<std::map<char, int> > data(arraysize);
    
        for (int j=0; j < 100000; ++j)
        {
            for (int i=0; i<arraysize; i++)
                a[i] = static_cast<char>('a' + i);
    
            if (choice == 1)
                BadShuffle(a, arraysize);
            else if (choice == 2)
                GoodShuffle(a, arraysize);
            else if (choice == 3)
                BuiltInShuffle(a, arraysize);
    
            for (int i=0; i<arraysize; i++)
                data[i][a[i]]++;
        }
    
        for (int index = 0; index < arraysize; ++index)
        {
            std::cout << '\n';
            OutputFreq(data, index);
            std::cout << '\n';
        }
    
        std::cin.get();
    }
    
    void OutputFreq(const std::vector<std::map<char, int> >& data, int index)
    {
        int lineCnt = 0;
        std::cout << "Frequency of char for index: " << index << std::endl;
        for (std::map<char, int>::const_iterator iter = data[index].begin(),
            end = data[index].end(); iter != end; ++iter)
        {
            std::cout << iter->first << ':' << iter->second << "   ";
    
            if (((++lineCnt) % 5) == 0)
                std::cout << std::endl;
        }
    }
    Here is an example output for index 0 in one run:
    Code:
    Frequency of char for index: 0
    a:3975   b:5350   c:5106   d:4941   e:4989
    f:4850   g:4695   h:4634   i:4427   j:4233
    k:4095   l:4143   m:3921   n:3822   o:3796
    p:3701   q:3557   r:3495   s:3301   t:3301
    u:3201   v:3185   w:3165   x:3082   y:3035

  7. #7
    Cheesy Poofs! PJYelton's Avatar
    Join Date
    Sep 2002
    Location
    Boulder
    Posts
    1,728
    Oops, you're right, its been awhile since I've had to implement this on my own. Looking back at my notes I meant this to prevent the skewing problem Daved mentioned:
    Code:
         swap (a[i], a[i+rand()%(arraysize-i)]);  // or implement your own swapping code here

Popular pages Recent additions subscribe to a feed

Similar Threads

  1. Generate Random Numbers and Assign to Days of Week
    By mms in forum C++ Programming
    Replies: 10
    Last Post: 05-04-2006, 01:51 AM
  2. Program Random Questions
    By mikeprogram in forum C++ Programming
    Replies: 3
    Last Post: 11-19-2005, 11:45 PM
  3. A question about C++ random generator and unsigned method
    By joenching in forum C++ Programming
    Replies: 13
    Last Post: 03-14-2005, 04:05 PM
  4. question about the loop in case conversion program
    By Elhaz in forum C++ Programming
    Replies: 8
    Last Post: 09-20-2004, 04:06 PM
  5. Replies: 2
    Last Post: 12-25-2003, 01:31 AM