Thread: A problem with nested for() loops

  1. #1
    Registered User
    Join Date
    Mar 2008
    Posts
    5

    A problem with nested for() loops

    Hi everyone,

    I'm struggling with the following problem and would appreciate your help very much:

    Write a program that reads in two natural numbers, m and n (m<n) and prints a zigzag graph composed of a series of two asterisks (**). The graph should start at the upper-left corner, and descend into line below so that asterisks in that line would be indented by two places, and when the graph reaches the bottom (m-th row), it should go upwards in the same fashion, and so on, until the n-th "column" is filled.

    For example, if the input is m=3 and n=21, the output should be:
    Code:
    **      **      **      
      **  **  **  **  **
        **      **      *
    or, if m=7 and n=33, the output should be:
    Code:
    **                      **
      **                  **  **
        **              **      **
          **          **          **
            **      **              *
              **  **
                **
    As I don't know how to use multidimensional arrays (matrices), this problem should be solved using only loops, ie for(), while() loops etc. So I tried and tried, but all I managed up until now is to "draw" only the first segment of the zigzag line:

    Code:
    #include <stdio.h>
    
    int main(void){
        unsigned int m, n, i, j;
    
        printf("Enter m:");
        scanf("&#37;d",&m);
        
        printf("Enter n:");
        scanf("%d",&n);
        
        if(m>=n) {printf("n should be strictly larger than m!\n"); return;}
        
        for(i=1;i<=m;i++){
                          for(j=1;j<=n;j++){
                                            if(j%2==0 && j==2*i) printf("*");
                                            if(j%2!=0 && j==((2*i)-1)) printf("*");
                                            else printf(" ");
                                          }
                                            
                          printf("\n");}
    
        return 0;}
    All this program does is, for example if m=6 and n=24, it prints only the first segment:

    Code:
    **
      **
        **
          **
            **
              **
    which is not nearly the desired solution. Then I tried calculating the length of "gaps" between two asterisks in an arbitrary row, for example in the case when m=5 and n=21,

    Code:
    i=1 **<-----14----->**
    i=2   **<---10--->**  **
    i=3     **<--6->**      *
    i=4       **-2**
    i=5         **
    and ended up with the formula sp=4*(m-i)-2, where sp is the number of spaces between two **'s in i-th row, but that didn't seem to be too useful...

    (E.g. in the above case, number of gaps between ** and ** in the second row, if total number of rows=5, is 4*(5-2)-2=10)

    Thank you very much for taking your time to read this, and if you have any idea how to solve this problem, I would be deeply grateful.
    Last edited by beorhtnoth; 03-24-2008 at 09:41 AM.

  2. #2
    Super unModrator
    Join Date
    Dec 2007
    Posts
    321
    All this program does is, for example if m=6 and n=24, it prints only the first segment
    I think you should print a whole row first because I don't think there is a way to get the cursor to move up once it has descended down.

    So the first time the loop is executed you should have something like this
    Code:
    **                  **
    Then during second execution print the second row below this.
    So after second execution of the loop it should look like
    Code:
    **                                  **
       **                            **   **
    ....or is there a way to move the cursor up (?)
    Last edited by abh!shek; 03-24-2008 at 10:19 AM.

  3. #3
    Registered User
    Join Date
    Mar 2008
    Posts
    5
    Quote Originally Posted by abk View Post
    I think you should print a whole row first because I don't think there is a way to get the cursor to move up once it comes down.

    So the first time the loop is executed you should have something like this
    Code:
    **                  **
    Then during second execution print the second row.
    Yes, I'm aware of that, i know everything should be printed line by line, so there should be at least two loops - one which goes from line to line (from 1st to m-th line), and the other, inside former loop, which goes from element to element (from 1st ti n-th), and by some criteria decides whether an '*' or space should be printed in that line.

    But I have problem determining these criteria; how to formulate them.

    Let's say the program is in the 4-th row (outer loop). It goes from the first to the last "letter" in that row and by some criteria decides whether that letter should be space or an asterisk.

    But how?

  4. #4
    Registered User
    Join Date
    Jan 2007
    Location
    Euless, TX
    Posts
    144
    I believe what you need is another array to hold your asterisk values. For example if the numbers are 7 and 33, you would need an array like this:

    char array[7][33]

    and what you are going to do is place those values from your 'for' loops into this array and print out this array by rows when you are done.

    Does that sound plausible for you to accomplish?

  5. #5
    Registered User
    Join Date
    Mar 2008
    Posts
    5
    Quote Originally Posted by kcpilot View Post
    I believe what you need is another array to hold your asterisk values. For example if the numbers are 7 and 33, you would need an array like this:

    char array[7][33]

    and what you are going to do is place those values from your 'for' loops into this array and print out this array by rows when you are done.

    Does that sound plausible for you to accomplish?
    I'm not sure really, I've ever only worked with one-dimensional arrays, of the type int array[x].

    Well, suppose I look up arrays of the type you mentioned, i.e. char array[7][33]. However, I'm not sure about this: those values (in brackets) should be arbitrary: the user enters x and y, and I'm not sure if char array[x][y] could be created afterwards.
    I believe that, e.g. int array[x] should be initialized at the beginning of the function, and not after scanf'ed values which would determine the size of the array.

    I've heard something about dynamic allocation but am not sure how complex is that to use...

  6. #6
    Nub SWE
    Join Date
    Mar 2008
    Location
    Dallas, TX
    Posts
    133
    If you're not comfortable with the concept of dynamic allocation using malloc(), you'll just have to create a two-dimensional array that will be large enough to handle a suitable range of input sizes that the user might give you. You'll possibly have a lot of extra space that goes unused, but without dynamic allocation, you'll just have to live with it.

  7. #7
    Registered User
    Join Date
    Jan 2008
    Posts
    290
    Code:
    #include <stdio.h>
    
    int main(int argc, char **argv) {
      int numrows, numcols, numspaces;
      int r, c, i, flip;
      
      if (argc < 3) return 1;
      
      sscanf(argv[1], "&#37;d", &numrows);
      sscanf(argv[2], "%d", &numcols);
      
      if (numrows < 1)
        return 0;
      
      if (numrows == 1) {
        for (i = 0; i < numcols; i++)
          putchar('*');
        return 0;
      }
      
      for (r = 0; r < numrows; r++) {
        for (c = 0; c < 2*r && c < numcols; c++)
          putchar(' ');
        
        flip = 0;
        
        while (c < numcols) {
          numspaces = flip ? 4 * r - 2
                           : 4 * (numrows - r - 1) - 2;
          
          if (numspaces > 0) {
            putchar('*');
            c++;
            if (c < numcols) {
              putchar('*');
              c++;
            }
            
            for (i = 0; c < numcols && i < numspaces; i++, c++)
              putchar(' ');
          }
          
          flip = !flip;
        }
        
        putchar('\n');
      }
    }
    Yes?
    Last edited by arpsmack; 03-24-2008 at 03:08 PM. Reason: Fixed printing of spaces at the beginning of empty rows

  8. #8
    Registered User
    Join Date
    Mar 2008
    Posts
    5
    Quote Originally Posted by arpsmack View Post
    Yes?
    Wow, thanks arpsmack! I seem to get the gist of this solution, although I've never encountered expressions such as argc and sscanf before (as you can see, I've still got much to learn). However, I'm flipping through my C manuals at this very moment and I hope to become acquainted with all those expressions in the foreseeable future.

    However, when I tried to run this program, nothing happened. I use Dev-C++ on WindowsXP and compiling went OK, but when I tried to run it (even in the command prompt!) absolutely nothing happened... I really have no idea where the problem might lie...

    Thank you very much for your help.

  9. #9
    Hurry Slowly vart's Avatar
    Join Date
    Oct 2006
    Location
    Rishon LeZion, Israel
    Posts
    6,788
    it should be run as

    <progname> <number>
    or
    <progname> <number> <number>

    for example:
    test.exe 3 5
    All problems in computer science can be solved by another level of indirection,
    except for the problem of too many layers of indirection.
    – David J. Wheeler

  10. #10
    Registered User
    Join Date
    Mar 2008
    Posts
    5
    Quote Originally Posted by vart View Post
    it should be run as

    <progname> <number>
    or
    <progname> <number> <number>

    for example:
    test.exe 3 5
    It works! Brilliant!

    This is exactly what I was after.

    Thank you arpsmack and everyone else for your help and patience.

  11. #11
    Registered User
    Join Date
    Feb 2008
    Posts
    26
    Isn't this a violation of the "Homework" policy. Please do not post complete solutions, it's important that people figure things out for themselves.

  12. #12
    Registered User
    Join Date
    Jan 2008
    Posts
    290
    I have read the "Homework Policy" that you reference and I don't remember reading anything about how I can't post a full solution to someone's problem.

    I read the previous posters who seemed to think that you NEEDED an array for this even though you clearly don't. Sure I could have posted something to the effect of, "Actually, this can be done without arrays." with an implied "neener neener I'm better than you", but I thought maybe some code would be a little clearer and much more helpful.

    Furthermore, all the work was actually done by the OP. I didn't need to find the formula for the number of spaces between asterisks because he already did it correctly. I simply turned it into a loop.

    On a final note, I just spent about 10 hours of my spring break trying to code a uniform grid filled with data points from a mathematical function in C++ using VTK. I needed to show some isosurfaces, cutting planes, and contoured cutting planes. My teacher showed me a sample program that does it, and now I can reliably do it to. It took me about 20 minutes to learn how from the code. 20 MINUTES to figure out what 10 hours of digging through horrible documentation and trial and error couldn't. Code speaks much louder than words to me, and I suspect to many.

Popular pages Recent additions subscribe to a feed

Similar Threads

  1. Laptop Problem
    By Boomba in forum Tech Board
    Replies: 1
    Last Post: 03-07-2006, 06:24 PM
  2. Replies: 5
    Last Post: 11-07-2005, 11:34 PM
  3. half ADT (nested struct) problem...
    By CyC|OpS in forum C Programming
    Replies: 1
    Last Post: 10-26-2002, 08:37 AM
  4. problem w/ nested templatized classes
    By *ClownPimp* in forum C++ Programming
    Replies: 8
    Last Post: 10-19-2002, 07:58 AM
  5. binary tree problem - help needed
    By sanju in forum C Programming
    Replies: 4
    Last Post: 10-16-2002, 05:18 AM