If you read existing C programs, you often see code similar to

Code:

/* 3D point (or 3D vector), data type. */
typedef struct {
double x;
double y;
double z;
} point_t;
/* "constructor" for simple assignments. */
point_t point(const double x, const double y, const double z)
{
point_t p;
p.x = x;
p.y = y;
p.z = z;
return p;
}
/* Return the dot product of two 3D vectors. */
double dot_product(const point_t v1, const point_t v2)
{
return v1.x*v2.x + v1.y*v2.y + v1.z*v2.z;
}
/* Return the cross product of two vectors. */
point_t cross_product(const point_t v1, const point_t v2)
{
point_t p;
p.x = v1.y * v2.z - v1.z * v2.y;
p.y = v1.z * v2.x - v1.x * v2.z;
p.z = v1.x * v2.y - v1.y * v2.x;
return p;
}

For square root, you'll need to include the <math.h> header, link against the math library (add -lm to your compiling command), and use the sqrt() function. (Or sqrtf(), if you are using single-percision floats instead of doubles.)

A side note:

An often overlooked feature of C is that structures can be copied and assigned. Givenmany programmers still write (the equivalent of)

Code:

p1.x = p2.x;
p1.y = p2.y;
p1.z = p2.z;

even though

is perfectly valid and works like you'd expect it to. Thus, with the point() function above, you can write code like

Code:

point_t p;
p = cross_product(point(1.0, 2.0, 3.0), point(-1.0, 0.0, -1.0));

If you use C99 (instead of ANSI C, C89/C90), you can use

Code:

#define _POSIX_C_SOURCE 200809L
#include <stdio.h>
/* 3D point (or 3D vector), data type.
*/
typedef struct {
double x;
double y;
double z;
} point_t;
/* Point "constructor" for easier coding. */
static inline point_t point(const double x, const double y, const double z)
{
return (point_t){ x, y, z };
}
/* Return the dot product of two 3D vectors. */
static inline double dot_product(const point_t v1, const point_t v2)
{
return v1.x*v2.x + v1.y*v2.y + v1.z*v2.z;
}
/* Return the cross product of two vectors. */
static inline point_t cross_product(const point_t v1, const point_t v2)
{
return (point_t){ v1.y * v2.z - v1.z * v2.y,
v1.z * v2.x - v1.x * v2.z,
v1.x * v2.y - v1.y * v2.x };
}

which tends to be faster code (since the basic operations are inlined, not called as functions, and the compiler can often optimize more complex math operations than when it could were they separate functions).