Thread: Stuck with Structs...

  1. #1
    Registered User
    Join Date
    Jun 2003
    Posts
    129

    Stuck with Structs...

    I've got one line (so far) in my program that doesn't want to play ball...

    Code:
    system[mapLocation[random, random2]].AdjSystem[planetAdderLoop] = subSystemNumber;
    these come from:

    Code:
    struct SystemStruct
    {
        ...
        private int[] adjSystems;
        public int[] AdjSystems;
        {
            get
            {
                return adjSystems;
            }
            set
            {
                adjSystems = value;
            }
        }
        ...
    }
    Code:
    SystemStruct[] system = new SystemStruct[650];
    and

    Code:
    int subSystemNumber = new int();
    Now, I've seen this at http://www.c-sharpcorner.com/UploadF...turesInCS.aspx

    Code:
    //C#: Property
    // Author: [email protected]
    using  System;
    class MyStruct
        private int x; 
        public int X 
        { 
            get 
            { 
                return x; 
            } 
            set 
            { 
                x = value; 
            } 
        }
    }
    class MyClient
        public static void Main() 
        { 
            MyStruct ms = new MyStruct(); 
            ms.X = 10; 
            int xVal = ms.X; 
            Console.WriteLine(xVal);//Displays 10 
        }
    }
    Is it the fact I'm arraying the variable I'm trying to use here? What do I do to change that system[x].AdjSystems[y] so that 'Object reference not set to an instance of an object.' stops screaming at me?
    He who asks is a fool for five minutes, but he who does not ask remains a fool forever.

    The fool wonders, the wise man asks. - Benjamin Disraeli

    There are no foolish questions and no man becomes a fool until he has stopped asking questions. Charles Steinmetz

  2. #2
    the hat of redundancy hat nvoigt's Avatar
    Join Date
    Aug 2001
    Location
    Hannover, Germany
    Posts
    3,130
    You didn't define how many adjSystems there for each of your 650 systems.

    private int[] adjSystems;

    Writing to any index in this array will throw an exception until you "new" something.

    Maybe you should use a container class like ArrayList if you don't know how many subsystems each system has.
    hth
    -nv

    She was so Blonde, she spent 20 minutes looking at the orange juice can because it said "Concentrate."

    When in doubt, read the FAQ.
    Then ask a smart question.

  3. #3
    Registered User
    Join Date
    Jun 2003
    Posts
    129
    oops, forgot to say i call this at start:

    Code:
    public void SpacePlan_Load(object sender, EventArgs e)
            {
                SystemStruct[] system = new SystemStruct[651];
                for (int loop1 = 0; loop1 <= 650; loop1++)
                {
                    system[loop1].AdjSystem = new int[7];
                }
            }
    um, ignore the 650 number, i changed the previous posts 650 to 651 (still same problem though).
    He who asks is a fool for five minutes, but he who does not ask remains a fool forever.

    The fool wonders, the wise man asks. - Benjamin Disraeli

    There are no foolish questions and no man becomes a fool until he has stopped asking questions. Charles Steinmetz

  4. #4
    Registered User
    Join Date
    Jun 2003
    Posts
    129
    I'm still stuck on this

    there are 650 (or so) 'system', and for each system there can be up to 7 adjsystem variables, unfortunately, the code does require that i have the ability to cycle through the the adjsystem variables, reading, writing etc.

    help!

    Edit: There may be up to 7, but there must always be 7 available. So there may only be one adjacent system, but at any point it must be possible to add more, up to a total of seven. The system struct actually has another property that counts the number of adjsystem for that particluar system, so that cycling through and other actions can be carried out easily.
    Last edited by DanFraser; 04-30-2007 at 09:49 AM.
    He who asks is a fool for five minutes, but he who does not ask remains a fool forever.

    The fool wonders, the wise man asks. - Benjamin Disraeli

    There are no foolish questions and no man becomes a fool until he has stopped asking questions. Charles Steinmetz

  5. #5
    Anti-Poster
    Join Date
    Feb 2002
    Posts
    1,401
    You'd probably get better answers if you actually showed some code. There's no way for us to test what you've got.

    Nevertheless, I can still blindly ask questions. Why are you using structs? What reason do you have for wanting value semantics over reference semantics? Note this wonderful little side effect of value semantics:
    Code:
    struct A
    {
    	int[] _ints;
    
    	public int[] Ints
    	{
    		get { return _ints; }
    		set { _ints = value; }
    	}
    }
    
    static void AddInts(A a)
    {
    	a.Ints = new int[7];
    }
    
    static void Main(string[] args)
    {
    	A a = new A();
    	AddInts(a);
    	if (a.Ints == null)
    		Console.WriteLine("Why?");
    }
    Personally, I default to classes unless I have a compelling reason to want value semantics.

    Why assign the integer arrays later instead of passing in a parameter on construction? Do you really want AdjSystems to be settable any time or only during construction?
    If I did your homework for you, then you might pass your class without learning how to write a program like this. Then you might graduate and get your degree without learning how to write a program like this. You might become a professional programmer without knowing how to write a program like this. Someday you might work on a project with me without knowing how to write a program like this. Then I would have to do you serious bodily harm. - Jack Klein

  6. #6
    Registered User
    Join Date
    Jun 2003
    Posts
    129
    I wonder how many characters each post can hold? Let's find out!

    Here's my struct:
    Code:
    struct SystemStruct
    {
        public int SystemType;
        public int SubSystems;
        public int AdjSystems;
        public int Pop;
        public int Ind;
        public bool NetLinked;
        public bool NetHome;
        public int NetLinkedTo;
        public int Production;
        public int Owner;
        public int Carriers;
        public int Escorts;
        public int Riders;
        public int Marines;
        public int Cruisers;
        public int Fighters;
        public int Militia;
        public int DefenceMode;// (0 = Retreat, 1 = Defend, 2 = Ambush)
        public int RetreatTo;
        public int DefendTowards;
        public int AmbushAgainst;
        public int[] AdjSystem
        {
            get
            {
                return adjSystem;
            }
            set
            {
                adjSystem = value;
            }
        }
        public int[] adjSystem;
        public int Income;
        public int ProdCost;
        public int Merchanters;
        public int FleetSupply;
        public int IndSupply;
        public int PopSupply;
        public int FO;
        public int HC;
        public int IS;
        public int MI;
        public int PopLimit;
        public int EcoDamage;
        public bool Visible;// (o = False, 1 = True);
        public bool Stuck;
        public bool Station;
    }
    From what I've read on the net, apparently this might be a good idea. Doesn't throw an error at compile or runtime.
    Code:
    public void SpacePlan_Load(object sender, EventArgs e)
            {
                SystemStruct[] system = new SystemStruct[651];
    
                for (int loop1 = 0; loop1 <= 650; loop1++)
                {
                    system[loop1].AdjSystem = new int[7];
                }
            }
    After a few button clicks, we get to this:
    Code:
    MapCreationRoutine();
    Which by code gets through to this, note that there are several uses of the struct 'system', no code errors, and breakpoint use confirms that the values are set to what they should be.
    Code:
    public void CreateStartPlaces()
    {
        Stack numberCheck = new Stack();
        Stack subsystemCheck = new Stack();
        int[] array1 = new int[13];
        for (startPlaceLoop = 1; startPlaceLoop <= 12; startPlaceLoop++)
        {
            // finds a suitable system
            do
            {
                StartPlaces1();
            }
            while (mapLocation[random, random2] == 0);
            // Now let's assign a random empire to the star system
            do
            {
                array1[startPlaceLoop] = rnd.Next(1, 13);
            }
            while (numberCheck.Contains(array1[startPlaceLoop]) == true);
            numberCheck.Push(array1[startPlaceLoop]);
            system[mapLocation[random, random2]].Owner = array1[startPlaceLoop];
            // sets the number of subsystems of the star system to 4
            system[mapLocation[random, random2]].SubSystems = 4;
            // also sets the number of adjacent systems to 4 as well
            system[mapLocation[random, random2]].AdjSystems = 4;
            subsystemCheck.Clear();
            for (int planetAdderLoop = 0; planetAdderLoop <= 3; planetAdderLoop++)// loop to add planets/asteroids
            {
                int subSystemNumber = new int();
                bool exists = true;
                // Now to assign the subsystems number, and add it to the
                // parent systems adjacent systems list
                while (exists == true)
                {
                    subSystemNumber = rnd4.Next(100, 600);
                    system[mapLocation[random, random2]].AdjSystem[planetAdderLoop] = subSystemNumber;
                    exists = mapLocCount.Contains(subSystemNumber);
                }
                //add the number to the 'list'
                mapLocCount.Push(subSystemNumber);
                // Can only be linked to its parent star, so adjacent systems = 1
                system[subSystemNumber].AdjSystems = 1;
                // here we add the parent system number to the first adjacent system slot
                system[subSystemNumber].AdjSystem[0] = mapLocation[random, random2];
                if (planetAdderLoop == 0) // if its the first subsystem, its a terran planet
                {
                    assignSysType = 13;
                    system[subSystemNumber].Owner = array1[startPlaceLoop];
                    countAsteroids = 0;
                }
                else // if its not the first subsystem, lets randomise !
                {
                   int AsteroidChance = 0;
                   if (countAsteroids > 1)
                   {
                       AsteroidChance = 18;
                   }
                   else
                    {
                        AsteroidChance = 21;
                    }
                    do
                    {
                       assignSysType = rnd2.Next(16, AsteroidChance);
                    }
                    while (subsystemCheck.Contains(assignSysType) == true);
                    if (assignSysType > 19)
                    {
                      assignSysType = 19;
                    }
                    if (planetAdderLoop == 21 && countAsteroids == 0)
                    {
                        assignSysType = 19;
                    }
               }
               if (assignSysType == 19)
               {
                    countAsteroids++;
               }
               if (assignSysType != 19)
               {
                   subsystemCheck.Push(assignSysType);
               }
                system[subSystemNumber].SystemType = assignSysType;
            }
        }
    }
    Code:
    public void MoreSubSystems()
            {
                for (mapy = 1; mapy <= 19; mapy++) //starts the standard map loop
                {
                    for (mapx = 1; mapx <= 19; mapx++)
                    {
                        if (mapLocation[mapy, mapx] > 0) // is there a system here? if no - break
                        {
                            if (system[mapLocation[mapy, mapx]].SubSystems == 0  // does it have any subsystems? if yes - break
                                && system[mapLocation[mapy, mapx]].SystemType != 12 // Is it a planetoid? if yes, break
                                && system[mapLocation[mapy, mapx]].SystemType != 11) // Is it a black hole? if yes, break
                            {
                                int subTypeCountRandomiser = rnd.Next(1, 101);//randomise for adding subsystems
                                if (subTypeCountRandomiser < 71)
                                {
                                    system[mapLocation[mapy, mapx]].SubSystems = 0;
                                }
                                if (subTypeCountRandomiser > 70 && subTypeCountRandomiser < 92)
                                {
                                    system[mapLocation[mapy, mapx]].SubSystems = 1;
                                }
                                if (subTypeCountRandomiser > 91 && subTypeCountRandomiser < 97)
                                {
                                    system[mapLocation[mapy, mapx]].SubSystems = 2;
                                }
                                if (subTypeCountRandomiser > 96 && subTypeCountRandomiser < 100)
                                {
                                    system[mapLocation[mapy, mapx]].SubSystems = 3;
                                }
                                if (subTypeCountRandomiser > 99)
                                {
                                    system[mapLocation[mapy, mapx]].SubSystems = 4;
                                }
                                system[mapLocation[mapy, mapx]].AdjSystems = system[mapLocation[mapy, mapx]].SubSystems;
                                if (system[mapLocation[mapy, mapx]].SubSystems > 0)
                                {
                                    for (loop1 = 0;
                                        loop1 < system[mapLocation[mapy, mapx]].SubSystems; loop1++)
                                    {
                                        int subSystemNumber = 0;
                                        bool exists = true;
                                        // Now to assign the subsystems number, and add it to the
                                        // parent systems adjacent systems list
                                        while (exists == true)
                                        {
                                            subSystemNumber = rnd4.Next(100, 600);
                                            system[mapLocation[mapy, mapx]].adjSystem[loop1] = subSystemNumber;
                                            exists = mapLocCount.Contains(subSystemNumber);
                                        }
                                        //add the number to the 'list'
                                        mapLocCount.Push(subSystemNumber);
                                        // Can only be linked to its parent star, so adjacent systems = 1
                                        system[subSystemNumber].AdjSystems = 1;
                                        // here we add the parent system number to the first adjacent system slot
                                        system[subSystemNumber].AdjSystem[0] = mapLocation[mapy, mapx];
                                        assignSysType = rnd2.Next(13, 21);
                                        if (assignSysType > 20)
                                        {
                                            assignSysType = 19;
                                        }
                                        system[subSystemNumber].SystemType = assignSysType;
                                    }
                                }
                            }
                        }
                    }
                }
            }
    Now, as you can see, the struct is mainly used for the fact it's nice and clear to read. All the values in it, apart from AdjSystem[x] work correctly, all assigned and readable etc. What I am wanting to do is to be able to have a value that i can cycle through very easily in loops etc for the adjsystem. There is more code to show, but there's so much it'd never fit in a whole thread.
    He who asks is a fool for five minutes, but he who does not ask remains a fool forever.

    The fool wonders, the wise man asks. - Benjamin Disraeli

    There are no foolish questions and no man becomes a fool until he has stopped asking questions. Charles Steinmetz

  7. #7
    Anti-Poster
    Join Date
    Feb 2002
    Posts
    1,401
    Here's a stab in the dark.
    Code:
    public void SpacePlan_Load(object sender, EventArgs e)
            {
                SystemStruct[] system = new SystemStruct[651];
    
                for (int loop1 = 0; loop1 <= 650; loop1++)
                {
                    system[loop1].AdjSystem = new int[7];
                }
            }
    ...
    public void CreateStartPlaces()
    {
            ...
            system[mapLocation[random, random2]].Owner = array1[startPlaceLoop];
    Note that CreateStartPlaces doesn't define any variable called 'system'. I'm guessing you've got some class member called 'system' since, as you say, it compiles for you.

    However, SpacePlan_Load defines a variable called 'system'. The initialization that you'd wanted done to your class member is actually being done to a local variable that's being lost at the end of scope. Where are you defining the 'system' that CreateStartPlaces is using?
    If I did your homework for you, then you might pass your class without learning how to write a program like this. Then you might graduate and get your degree without learning how to write a program like this. You might become a professional programmer without knowing how to write a program like this. Someday you might work on a project with me without knowing how to write a program like this. Then I would have to do you serious bodily harm. - Jack Klein

  8. #8
    Registered User
    Join Date
    Jun 2003
    Posts
    129
    Code:
    namespace SpacePlanII
    {
        public partial class SpacePlan : Form
        {
            ...
            SystemStruct[] system = new SystemStruct[650];
            ...
        }
    }
    No idea why I put that second one in SpacePlan_Load(...).
    He who asks is a fool for five minutes, but he who does not ask remains a fool forever.

    The fool wonders, the wise man asks. - Benjamin Disraeli

    There are no foolish questions and no man becomes a fool until he has stopped asking questions. Charles Steinmetz

  9. #9
    Registered User
    Join Date
    Jun 2003
    Posts
    129
    Ok, I removed the new Struct in SpacePlan_Load and modified the code to something similar, everything seems ok... The for loop is still there though.

    I just have to work through every use of this new system of using the values to correct it all...
    He who asks is a fool for five minutes, but he who does not ask remains a fool forever.

    The fool wonders, the wise man asks. - Benjamin Disraeli

    There are no foolish questions and no man becomes a fool until he has stopped asking questions. Charles Steinmetz

Popular pages Recent additions subscribe to a feed

Similar Threads

  1. Creating array of structs
    By knirirr in forum C++ Programming
    Replies: 12
    Last Post: 06-18-2008, 08:30 AM
  2. Multidimentional structs + memcpy() == FAIL
    By Viper187 in forum C Programming
    Replies: 8
    Last Post: 06-18-2008, 02:46 AM
  3. packed structs
    By moi in forum C Programming
    Replies: 4
    Last Post: 08-20-2002, 01:46 PM
  4. ArrayLists + Inner Structs
    By ginoitalo in forum C# Programming
    Replies: 5
    Last Post: 05-09-2002, 05:09 AM
  5. Searching structs...
    By Sebastiani in forum C Programming
    Replies: 1
    Last Post: 08-25-2001, 12:38 PM