Thread: Best Practices for Operations on Structures

  1. #1
    Registered User
    Join Date
    Feb 2009
    Posts
    20

    Best Practices for Operations on Structures

    For a program I am working on, I need to perform some operations on vectors, such as vector addition. However, I am unsure of how best to write the functions to perform the operation. My vector is defined as
    Code:
    struct Vector
    {
      double x;
      double y;
      double z;
    };
    If I want to add two vectors together and return a vector, is there a general best practice for one of these forms?

    Code:
    Vector * vector_add_1(Vector *v1, Vector *v2)
    {
      Vector *sum = malloc(sizeof(Vector));
    
      /* Assign values to sum */
      return sum;
    }
    
    void vector_add_2(Vector *v1, Vector *v2, Vector *dest)
    {
      dest->x = ...;
        /* Snip */
    
      return;
    }
    Assume the latter function accounts for the case that dest could be v1 and/or v2.

  2. #2
    ATH0 quzah's Avatar
    Join Date
    Oct 2001
    Posts
    14,826
    If you aren't modifying the contents of the structure, you don't need to use a pointer, unless it's really huge for some reason (or I suppose unless you're regularly working with pointers to your structures, and you just want to keep the syntax the same).

    If you are only modifying the contents of the structure, and not the actual structure, for your sum, then a pointer is fine. Otherwise, you'll want a pointer to a pointer. It's just a matter of preference.


    Quzah.
    Hope is the first step on the road to disappointment.

  3. #3
    Registered User
    Join Date
    Feb 2009
    Posts
    20
    I will be modifying the contents of the structure. With the first function, I would create the structure and do a shallow copy, which I guess is a rather silly method. I suppose it would get much more complicated with pointers in the struct, wouldn't it?

  4. #4
    and the Hat of Guessing tabstop's Avatar
    Join Date
    Nov 2007
    Posts
    14,336
    We're getting a little bit of contradiction here, 'cause it's a long way from "adding vectors" to anything requiring modifying the contents of a structure, let alone a structure with pointers in it.

    (I don't remember what the old standard says, but C99 allows you to return a structure from a function, so for instance that first example should just be
    Code:
    Vector add(Vector left, Vector right) {
        Vector answer;
        answer.x = left.x + right.x;
        answer.y = left.y + right.y;
        answer.z = left.z + right.z;
        return answer;
    }
    and everybody's good.)

  5. #5
    Registered User
    Join Date
    Feb 2009
    Posts
    20
    Thanks for the help. Part of my question was determining a best practice. I was assuming I could not return a structure from a function. As far as asking about structures with pointers in them, I was thinking of the general case and possibly other functions in my program.

  6. #6
    ATH0 quzah's Avatar
    Join Date
    Oct 2001
    Posts
    14,826
    It doesn't really matter what's in the structure. Just how you pass it. Pass it by value, if you only want to look at what it has. Pass a pointer if you want to change what it has. Pass a pointer to that pointer, if you want to change what you're pointing at.


    Quzah.
    Hope is the first step on the road to disappointment.

  7. #7
    Woof, woof! zacs7's Avatar
    Join Date
    Mar 2007
    Location
    Australia
    Posts
    3,459
    > I don't remember what the old standard says, but C99 allows you to return a structure from a function
    So does C89.

    What I'd do is create a function to return a Vector, and use that from other functions, ie:

    Code:
    Vector init(const double x, const double y, const double z)
    {
       Vector result;
    
       result.x = x;
       result.y = y;
       result.z = z;
    
       return result;
    }
    
    
    Vector add(const Vector left, const Vector right)
    {
       return init(   left.x + right.x,
                      left.y + right.y,
                      left.z + right.z);
    }
    Some may argue that's harder to read, but it allows you to add additional members / initialisation with ease.

    You could also just use the "left" vector to store the result in a lot of operations (providing it wasn't const), since you'd have a copy of the original.
    Last edited by zacs7; 09-14-2009 at 01:45 AM.

  8. #8
    Registered User
    Join Date
    Aug 2009
    Posts
    198
    I thought that if you pass a structure (not a pointer), it creates a new copy of that structure (which is just a lump of primitive data types in a row in RAM) and so any modifications will not be carried on to the original one. Or at least that's what I think. Maybe I'll test it.

  9. #9
    and the Hat of Guessing tabstop's Avatar
    Join Date
    Nov 2007
    Posts
    14,336
    Quote Originally Posted by MTK View Post
    I thought that if you pass a structure (not a pointer), it creates a new copy of that structure (which is just a lump of primitive data types in a row in RAM) and so any modifications will not be carried on to the original one. Or at least that's what I think. Maybe I'll test it.
    That's right, but the point being you can return the newly-whatever'ed struct back to the main (so not pass by reference, but returning a value).

  10. #10
    Registered User
    Join Date
    Aug 2009
    Posts
    198
    Quote Originally Posted by tabstop View Post
    That's right, but the point being you can return the newly-whatever'ed struct back to the main (so not pass by reference, but returning a value).
    I still don't quite understand. I made this program:

    Code:
    #include <stdio.h>
    #include <stdlib.h>
    
    struct test
    {
    	int var;
    };
    
    void add(struct test a, int num) {
    	a.var += num;
    }
    
    void addptr(struct test* a, int num) {
    	a->var += num;
    }
    
    int main()
    {
    	struct test* a = malloc(sizeof(struct test));
    	a->var = 0;
    
    	printf("Initial var : %d\n", a->var);
    
    	add(*a, 1);
    
    	printf("Add 1 (copy): %d\n", a->var);
    
    	addptr(a, 1);
    
    	printf("Add 1  (ptr): %d\n", a->var);
    
    	free(a);
    
    	return 0;
    }
    And it prints out:

    Code:
    Initial var : 0
    Add 1 (copy): 0
    Add 1  (ptr): 1

  11. #11
    ATH0 quzah's Avatar
    Join Date
    Oct 2001
    Posts
    14,826
    Your programs functions don't return anything, so I'm not sure what your post is about really.


    Quzah.
    Hope is the first step on the road to disappointment.

  12. #12
    Registered User
    Join Date
    Aug 2009
    Posts
    198
    That's right, instead of having to return a new struct, my addptr() function just modifies the existing one.

  13. #13
    ATH0 quzah's Avatar
    Join Date
    Oct 2001
    Posts
    14,826
    Yes I know what it does. What I don't know is how it relates at all to what you've quoted. What you've quoted was about returning structures, and you aren't, but you're implying your code has something to do with that. Which it doesn't.


    Quzah.
    Hope is the first step on the road to disappointment.

  14. #14
    Registered User
    Join Date
    Aug 2009
    Posts
    198
    I see now. But it still seems like it is more efficient to pass pointers because new copies of the structs do not need to be made.

  15. #15
    Registered User
    Join Date
    Feb 2009
    Posts
    20
    What if I am using larger structures, say 5 MB images? I clearly do not want to return that on the stack. Is there a preferred way to return the new data in that case?

Popular pages Recent additions subscribe to a feed

Similar Threads

  1. Replies: 2
    Last Post: 07-11-2008, 07:39 AM
  2. Structures within Structures
    By Misko82 in forum C Programming
    Replies: 2
    Last Post: 08-27-2007, 12:25 AM
  3. Input output with structures
    By barim in forum C Programming
    Replies: 10
    Last Post: 04-27-2004, 08:00 PM
  4. pointers to arrays of structures
    By terryrmcgowan in forum C Programming
    Replies: 1
    Last Post: 06-25-2003, 09:04 AM
  5. Methods for Sorting Structures by Element...
    By Sebastiani in forum C Programming
    Replies: 9
    Last Post: 09-14-2001, 12:59 PM

Tags for this Thread