Thread: Langton's ant issue

  1. #1
    Registered User
    Join Date
    Jan 2014
    Posts
    6

    Langton's ant issue

    Hi,

    I've been trying for a while now to figure this problem out on my own, but nothing really useful popped up in my head. I'm trying to program the so called "Langton's ant" in C.
    The program should do the following:
    - Create an area of the size of the users choice
    - Place the 'ant' in the middle of the area
    - Everytime the ant moves (it looks down at the beginning and moves on 'step' per time), a function should check whether the field (array) is empty ' ' oder has a '#' inside. If if its blank, the ant puts a '#', moves 90° to the right and continues one step. If the field is already filled with a '#' it changes it back to blank, turns 90° degrees left and moves one step forward.
    As long as it didnt hit the border of the area, the function should return true and the programm should continue.

    This is what I have so far (some things are still inside for testing purpose). I hope someone can give me a helping hint. I'm a bit confused by all this pointers and stuff.

    Last but not least, sorry for me english, as it is not my native language.

    main.c
    *******
    Code:
    #include <stdio.h>
    #include "area.h"
    
    int nextStep (struct Ameise insect*,int len, char[][len]){
        // ???
    }
    
    int main ()
    {
    
      char test [][5] = {"ABCDE",
                         "BCDEA",
                         "CDEAB",
                         "DEABC",
                         "EABCD"};
      showArea (5, test);
      initArea (5, test);
      showArea (5, test);
      printf ("\n");
    
      // Eingaben
      int laenge;
      printf ("Groesse Spielfeld: ");
      scanf ("%d", &laenge);
    
      if (laenge < 1)
      {
        printf ("Zu klein!\n");
        return 9998;
      }
      //einfuehren der ameise, x und y koordinaten -> mittige position, blickrichtung unten, also 2
      struct Ameise insect = {(laenge/2),(laenge/2),2};
    
      printf ("\n");
    
      // Spielfeld anlegen (variable Länge)
      char raster[laenge][laenge];
    
      // Spielfeld wird belegt (Leerzeichen)
      initArea (laenge, raster);
    
      // Mitte des Spielfeld
      // alter text raster [laenge/2][laenge/2] = 'M';
      raster [laenge/2][laenge/2] = '#';
      // Hinweis: Die Mitte liegt nur exakt, wenn 'laenge' ungerade ist.
      // Für eine gerade 'laenge' nehmen wir die entsprechende Abweichung hin.
    
      // Ausgabe des Spielfelds
      showArea (laenge, raster);
    
      return 0;
    }
    area.c
    ******
    Code:
    #include <stdlib.h>
    #include "area.h"
    
    void initArea (int len, char area[][len]){
        for(int i=0;i<len;i++){
                for(int j=0;j<len;j++)
                    area[i][j] = ' ';
        }
    }
    
    void showArea (int len, char area[][len]){
        printline(len);
        for(int i=0;i<len;i++){
                printf("|");
                for(int j=0;j<len;j++)
                    printf("%c", area[i][j]);
                printf("|\n");
        }
        printline(len);
    }
    
    void printline (int len){
        printf("+");
        for(int i=0;i<len;i++)
            printf("-");
        printf("+\n");
    }
    area.h
    ******
    Code:
    extern void printline(int len);
    extern void initArea(int len, char area[][len]);
    extern void showArea(int len, char area[][len]);
    extern struct Ameise{
        int x;
        int y;
        int blick;
    };
    Thanks in advance.
    Cheers.

  2. #2
    and the Hat of Guessing tabstop's Avatar
    Join Date
    Nov 2007
    Posts
    14,336
    What's your question?

  3. #3
    Registered User
    Join Date
    Sep 2006
    Posts
    8,868
    Welcome to the forum, wallet_22.

    The key to understanding the logic, will be revealed best, if you make a penny into your "ant", and work through it several times, on a table top, playing it by hand only. We learn best by doing! After a few dozen moves, you'll begin to see the patterns of logic that are repeated time after time, much more clearly.

    That becomes the backbone of the logic for your program.

  4. #4
    Registered User
    Join Date
    Jan 2014
    Posts
    6
    Hey,
    I have modified my main.c file and so far it is looking like the attached one. The Header file and the other file I didn't touch. How I Need modify my code, that the Program stops working when the ant hits the border of the Arena and gives a message like "Crash. 129 steps done". I tried it with anther else if Statement in the function but it didnt work out
    Any ideas?

    Code:
    #include <stdio.h>
    #include <stdlib.h>
    #include "area.h"
    int nextStep(struct Ameise* ant, int len, char antarena[][len]){
         if(antarena[ant->y][ant->x] == ' '){
             antarena[ant->y][ant->x] = '#';
             ant->blick = (ant->blick +1) %4;
             if(ant->blick == 0) ant->y = ant->y+1;
         if(ant->blick == 1) ant->x = ant->x+1;
         if(ant->blick == 2) ant->y = ant->y-1;
         if(ant->blick == 3) ant->x = ant->x-1;
         return 1;
         }
         else if(antarena[ant->y][ant->x] == '#'){
             antarena[ant->y][ant->x] = ' ';
             ant->blick = (ant->blick +3) %4;
             if(ant->blick == 0) ant->y = ant->y+1;
         if(ant->blick == 1) ant->x = ant->x+1;
         if(ant->blick == 2) ant->y = ant->y-1;
         if(ant->blick == 3) ant->x = ant->x-1;
         return 1;
         }
         else if(antarena[ant->y][ant->x] == '-'){
             return 3;
         }
         else if(antarena[ant->y][ant->x] == '|'){
             return 3;
         }
         else
            return 3;
    /*
         if(ant->blick == 0) ant->y = ant->y+1;
         if(ant->blick == 1) ant->x = ant->x+1;
         if(ant->blick == 2) ant->y = ant->y-1;
         if(ant->blick == 3) ant->x = ant->x-1;
         return 0;*/
    }
    int main (){
       // Einlesen der Spielfeld Groesse und Schritte
       int laenge;
       printf ("Rastergroesse: ");
       scanf ("%d", &laenge);
       if (laenge < 1){
         printf ("Zu klein!\n");
         return 9997;
       }
       printf ("\n");
       int anzSchritte;
       printf ("Schrittzahl: ");
       scanf ("%d", &anzSchritte);
       if (anzSchritte < 1){
         printf ("Zu klein!\n");
         return 9998;
       }
       printf ("\n");
       struct Ameise insect = {(laenge/2), (laenge/2), 2};
       struct Ameise* insectZeiger = &insect;
       char raster[laenge][laenge];
       initArea (laenge, raster);
       /*for(int i = 0; i <= anzSchritte; i++){
           nextStep(insectZeiger, laenge, raster);
       }
       showArea(laenge,raster);*/
       for(int i = 0; i < anzSchritte; i++){
           if((nextStep(insectZeiger, laenge, raster))== 1){
            }
            else if((nextStep(insectZeiger, laenge, raster))== 3){
                printf("Gecrasht bei %u",i);
                break;
            }
       }
    showArea(laenge,raster);
       return 0;
    }

  5. #5
    - - - - - - - - oogabooga's Avatar
    Join Date
    Jan 2008
    Posts
    2,808
    You have duplicate code. And you could use a switch.
    Code:
    int nextStep(struct Ameise* ant, int len, char antarena[][len]){
        switch (antarena[ant->y][ant->x]) {
        case ' ':
            antarena[ant->y][ant->x] = '#';
            ant->blick = (ant->blick +1) %4;
            break;
        case '#':
            antarena[ant->y][ant->x] = ' ';
            ant->blick = (ant->blick +3) %4;
            break;
        default:
            return 3;
        }
    
    
        switch (ant->blick) {
        case 0: ++ant->y; break;
        case 1: ++ant->x; break;
        case 2: --ant->y; break;
        case 3: --ant->x; break;
        return 1;
    }
    The cost of software maintenance increases with the square of the programmer's creativity. - Robert D. Bliss

  6. #6
    Registered User
    Join Date
    Jan 2014
    Posts
    6
    Thank you I was testing around and copying stuff in and out - anyway, I would have cleaned up the code afterwards.

    I'm still having the big issue, that the program doesnt stop, when the ant hits the Arena border and prints the steps which are done so far in the console. Do you have an idea? (I know that with an area size of 77, the ant can make 11045 steps before crashing, or in my Programm coming out on the other side of the arena...)

  7. #7
    - - - - - - - - oogabooga's Avatar
    Join Date
    Jan 2008
    Posts
    2,808
    You're running your function twice for each iteration.
    Try this (untested) :
    Code:
      for(int i = 0; i < anzSchritte; i++){
            if((nextStep(insectZeiger, laenge, raster)) == 3){
                printf("Gecrasht bei %u",i);
                break;
            }
       }
    The cost of software maintenance increases with the square of the programmer's creativity. - Robert D. Bliss

  8. #8
    Registered User
    Join Date
    Jan 2014
    Posts
    6
    No it doesnt change something. I think it's because the function cannot recognize the borders. I tried to check with the function if there is a "-" or an "|" but i think the Arena is just displayed and not really inside the Array which the function is going trough and replacing "#" and " ".
    ... I hope this sentence is understandable because it Looks a bit weird.

    My Logical idea (I couldnt program it yet) is:
    The ant starts always in the middle, so you take the half of the area size (e.g. size 10 will be 5) and call it border_x. When the ant makes a move on the x-achsis, this value will increase or decrease. if it hits 10 or 0, the Program Ends with the message, because the ant hits a wall.
    The same Thing Needs to be done for the y-achsis as the Arena is a square.
    I dont know how to set two variables in the main function, let them be checked and edited by the function and giving them both back to the main function, to check now inside the for-Loop, if the program should stop or not.
    Last edited by wallet_22; 01-29-2014 at 01:28 PM.

  9. #9
    - - - - - - - - oogabooga's Avatar
    Join Date
    Jan 2008
    Posts
    2,808
    Putting your code together with my changes and entering 20 and 100 yields:
    Code:
    +--------------------+
    |                    |
    |                    |
    |                    |
    |                    |
    |                    |
    |                    |
    |         ##         |
    |        #  #        |
    |       #  #         |
    |       #   #        |
    |        # ###       |
    |          #  #      |
    |          #  #      |
    |         #  #       |
    |          ##        |
    |                    |
    |                    |
    |                    |
    |                    |
    |                    |
    +--------------------+
    EDIT: Now that I think about it (and read your post), you're right that you need to check for the boundaries numerically. You're right, of course, that the border characters aren't in the array, so you can't check them. You could put them in the array, but it's probably best to test x and y against 0 and len.
    Code:
    if (ant->x < 0 || ant->x >= len || ant->y < 0 || ant->y >= len)
        return 3;
    Try putting that into your nextStep function at some appropriate spot.
    Last edited by oogabooga; 01-29-2014 at 01:47 PM.
    The cost of software maintenance increases with the square of the programmer's creativity. - Robert D. Bliss

  10. #10
    Registered User
    Join Date
    Jan 2014
    Posts
    6
    Yes, but enter an area size of "77" and a step amound of 12.000. The program does not stop at 11045 which it should normally do but continues to walk all the 12.000 steps.
    EDIT: Just saw your edit, let me try...
    Last edited by wallet_22; 01-29-2014 at 01:47 PM.

  11. #11
    Registered User
    Join Date
    Jan 2014
    Posts
    6
    Thats working!! Thanks alot, you really helped me out : ))

Popular pages Recent additions subscribe to a feed

Similar Threads

  1. An issue with pow()
    By Northe7 in forum C Programming
    Replies: 18
    Last Post: 09-20-2012, 06:49 AM
  2. bandwidth issue / network issue with wireless device communication
    By vlrk in forum Networking/Device Communication
    Replies: 0
    Last Post: 07-05-2010, 11:52 PM
  3. DNS issue
    By George2 in forum C# Programming
    Replies: 1
    Last Post: 08-02-2008, 10:15 AM
  4. What is the issue?
    By al_engler in forum C Programming
    Replies: 2
    Last Post: 12-19-2006, 01:54 PM
  5. my first issue of GDM
    By DavidP in forum A Brief History of Cprogramming.com
    Replies: 0
    Last Post: 09-12-2002, 04:02 PM