memcpy to copy local array of struct into local array of struct - memcpy

In C language, I want to copy 1 local array of structure into other local array of structure. Sample code example below. Which is the correct way to use memcpy() in this case?
'#define CAPACITY 5
int main(void)
{
typedef struct Prototype
{
int value;
} Prototype;
int i;
Prototype vProto1[CAPACITY], vProto2[CAPACITY];
for (i=0; i<CAPACITY; i++)
{
vProto1[i].value = i+1;
}
Here I want to copy vProto1 into vProto2. Is below command correct?
memcpy(vProto2, vProto1, sizeof(Prototype) * CAPACITY);
OR this is correct?
memcpy(&vProto2, &vProto1, sizeof(Prototype) * CAPACITY);
Thanks in advance. I am confused whether I should use "&" or not.

Related

Structure pointer dereference

I am trying to pass a structure of point array as shown, how can I correctly dereference the address to change the value the address points to.
// header file "header.h"
typedef struct {
double x;
double y;
} Pointbase;
typedef Pointbase *XYpt;
typedef struct {
XYpt xy[1];
} ChartPointsbase;
typedef ChartPointsbase **PointArray;
#include "header.h"
...
void npCluster(double drop, XYpt *newpt, PointArray outpts)
{
double xx[2]={-15, 100};
int i;
outpts = (PointArray)malloc(sizeof(PointArray) * 2);
for (i=0;i<2; i++)
{
(*(*outpts)->xy[i])->x=xx[i];
(*(*outpts)->xy[i])->y=drop;
}
}
The complier likes the following line but does not compute
(*outpts)->xy[i]->y=drop;
Any suggestions will be most appreciated.
I figured it out for "c" compiler as follows:
Define struct with two 1D arrays each of size dimsize, allocate memory to handles, set the size =k, and dereference as follows:
for (i=0; i<k; i=i++)
{
(*(outpts->xx))->dat[i]=135*i+j;
(*(outpts->yy))->dat[i]=drop;
}
For further nesting, say struct array of the above with two unequal point arrays, where cht is an array of PointArray
typedef struct {
int32 dimSize;
C1Hdl cht[1];
} XYchartCluster;
// initialize 1st array
for (i=0; i<k; i=i++)
{
(*(*(xycht)->cht[0])->xx)->dat[i]=135*i+j;
(*(*(xycht)->cht[0])->yy)->dat[i]=drop;
}
// initialize 2nd array with values from point npt
for (i=0; i<sz; i=i++)
{
(*(*(xycht)->cht[1])->xx)->dat[i]=npt->x;
(*(*(xycht)->cht[1])->yy)->dat[i]=npt->y;
}
/*
Note: size of each array in chart should be initialized and
memory assigned (dynamically changing size)
*/

Arduino Dynamic Two-dimensional array

I'm working on an Arduino project where I need to build (and work with) a two-dimensional array at runtime. I've been poking around looking for a solution, but I've had no luck. I found an example of a dynamic one-dimentional array helper here: http://playground.arduino.cc/Code/DynamicArrayHelper, so i've been trying to adopt that code for my use. I created a library using the following code:
My Header file:
#ifndef Dynamic2DArray_h
#define Dynamic2DArray_h
#include "Arduino.h"
class Dynamic2DArray
{
public:
Dynamic2DArray( bool sorted );
//Add an integer pair to the array
bool add( int v1, int v2);
//Clear out (empty) the array
bool clear();
//Get the array item in the specified row, column
int getValue(int row, int col);
//Get the number of rows in the array
int length();
private:
int _rows;
void * _slots;
bool _sorted;
void _sort();
};
#endif
The library's code:
#include "Arduino.h"
#include "Dynamic2DArray.h"
#define ARRAY_COLUMNS 2
int _rows;
void * _slots;
bool _sorted;
Dynamic2DArray::Dynamic2DArray(bool sorted) {
//Set our local value indicating where we're supposed to
//sort or not
_sorted = sorted;
//Initialize the row count so it starts at zero
_rows = 0;
}
bool Dynamic2DArray::add( int v1, int v2) {
//Add the values to the array
//implementation adapted from http://playground.arduino.cc/Code/DynamicArrayHelper
//Allocate memory based on the size of the current array rows plus one (the new row)
int elementSize = sizeof(int) * ARRAY_COLUMNS;
//calculate how much memory the current array is using
int currentBufferSize = elementSize * _rows;
//calculate how much memory the new array will use
int newBufferSize = elementSize * (_rows + 1);
//allocate memory for the new array (which should be bigger than the old one)
void * newArray = malloc ( newBufferSize );
//Does newArray not point to something (a memory address)?
if (newArray == 0) {
//Then malloc failed, so return false
return false;
}
// copy the data from the old array, to the new array
for (int idx = 0; idx < currentBufferSize ; idx++)
{
((byte*)newArray)[idx] = ((byte *)_slots)[idx];
}
// free the original array
if (_slots != NULL)
{
free(_slots);
}
// clear the newly allocated memory space (the new row)
for (int idx = currentBufferSize; idx < newBufferSize; idx++)
{
((byte *)newArray)[idx] = 0;
}
// Store the number of rows the memory is allocated for
_rows = ++_rows;
// set the array to the newly created array
_slots = newArray;
//Free up the memory used by the new array
free(newArray);
//If the array's supposed to be sorted,
//then sort it
if (_sorted) {
_sort();
}
// success
return true;
};
int Dynamic2DArray::length() {
return _rows;
};
bool Dynamic2DArray::clear() {
//Free up the memory allocated to the _slots array
free(_slots);
//And zero out the row count
_rows = 0;
};
int Dynamic2DArray::getValue(int row, int col) {
//do we have a valid row/col?
if ((row < _rows) && (col < ARRAY_COLUMNS)) {
//Return the array value at that row/col
return _slots[row][col];
} else {
//No? Then there's nothing we can do here
return -1;
}
};
//Sorted probably doesn't matter, I can probably ignore this one
void _sort() {
}
The initial assignment of the _slots value is giving me problems, I don't know how to define it so this code builds. The _slots variable is supposed to point to the dynamic array, but I've got it wrong.
When I try to compile the code into my project's code, I get the following:
Arduino: 1.8.0 (Windows 10), Board: "Pro Trinket 3V/12MHz (USB)"
sketch\Dynamic2DArray.cpp: In member function 'int Dynamic2DArray::getValue(int, int)':
sketch\Dynamic2DArray.cpp:83:22: warning: pointer of type 'void *' used in arithmetic [-Wpointer-arith]
return _slots[row][col];
^
Dynamic2DArray.cpp:83: error: 'void*' is not a pointer-to-object type
Can someone please help me fix this code? I've posted the files to https://github.com/johnwargo/Arduino-Dynamic-2D-Array-Lib.
The code you took was for a 1D dynamic array; the modifications for a 2D array are too tricky. Give up these horrors.
I think there is no reason you use dynamic array. You can assume that size max is ROW_MAX * COL_MAX, so you can define a static array int array[ROW_MAX][COL_MAX].
on one hand if you defined a dynamic array, you could free space when you dont use it anymore and take advantage of it for other work. I dont know if this is your case.
on the other hand if you define a static array (on UNO), you have 32kB available on program space, instead of 2kB available on RAM.
Because of the difference 32kB / 2kB, there are very few chances you can get bigger array with dynamic allocation.

Why can't I use the -> operator for a struct pointer in main?

I thought that the general rule of thumb was that the -> operator was used for accessing members of struct pointers, and the . operator was used for accessing members of an actual struct. In my code, I thought I created a struct pointer, but I ended up still having to use the . operator. Can someone explain why?
typedef struct Robot
{
char **brain;
int size;
} Robot;
int main(void)
{
char buffer[100];
Robot *dalek = malloc(sizeof(Robot)*2);
for(i = 0; i < 2; i++)
dalek[i].brain = malloc(sizeof(char*) * 3);
for(i = 0; i < 3; i++)
{
scanf("%s", buffer);
dalek[0].brain[i] = malloc(sizeof(char) * strlen(buffer));
strcpy(dalek[0].brain[i], buffer);
}
}
dalek is a pointer, and dalek[i] is equivalent to *(dalek + i), i.e. it dereferences. If you want to use the arrow, say (dalek + i)->brain etc.
dalek[i] is defined as *(dalek+i). So when you do dalek[i]->brain you are really doing *(*(dalek+i)).brain, dereferencing a single pointer twice. If you really want to use the -> operator, you could use (dalek+i)->brain.

error: request for member "machine" in something not a structure or union

When I'm trying to compile below program I'm getting error as request for member "machine" in something not a structure or union
struct machine
{
int a;
int b;
int c;
};
struct config
{
struct machine *machine;
int n;
};
int main()
{
struct config *conf;
struct machine *mach;
mach->a=1;
mach->b=2;
mach->c=3;
conf.machine=mach; /* error in this line */
return 0;
}
Can anyone help me in fixing this bug.. Thanks in advance!!!
conf is a pointer, not a structure, so you have to dereference it, just like you did with mach.
conf->machine = mach;
Also, you need to allocate memory for both conf and mach.

gcc: /home/jamie/aws/btree_int.c|28|error: request for member ‘btree_start’ in something not a structure or union|

This code:
#include <stdlib.h>
#include <stdio.h>
int j_btree_create (int fn_initial_nodes);
typedef struct {
int depth;
int value;
void *item;
void *left_pointer;
void *right_pointer;
} j_btree_node_int;
typedef struct {
int nodes;
int available_nodes;
int btree_extension;
} j_btree_descriptor_int;
int j_btree_create (int fn_initial_nodes) {
int *free_btree_node;
int loop_counter;
j_btree_descriptor_int *btree_start;
btree_start = (j_btree_descriptor_int *) malloc (((sizeof(j_btree_node_int) + sizeof(free_btree_node)) * fn_initial_nodes) + sizeof(j_btree_descriptor_int));
printf ("btree_start: " . btree_start);
/* *btree_start.nodes = fn_initial_nodes;
*btree_start.available_nodes = fn_initial_nodes;
*btree_start.extension = NULL; */
for (loop_counter = 0; loop_counter < fn_initial_nodes; loop_counter++) {
printf ("loop_test:" . loop_counter);
}
}
Produces this error:
/home/jamie/aws/btree_int.c||In function ‘j_btree_create’:|
/home/jamie/aws/btree_int.c|28|error: request for member ‘btree_start’ in something not a structure or union|
/home/jamie/aws/btree_int.c|33|error: request for member ‘loop_counter’ in something not a structure or union|
||=== Build finished: 2 errors, 0 warnings ===|
When compiled with CodeBlocks. I have not managed to find an exact answer to my problem (I have looked), does anyone know roughly what I am doing wrong? Probably more than one thing given I am fairly new to C.
printf ("btree_start: " . btree_start);
This is not how the things are done in c. There's no . concatenation operator and you do not concatenate strings (pointers to characters) and pointers to structures. If you want to print out the pointer, it's
printf("btree_start: %p\n",btree_start);
For the loop counter it's
printf("loop_test: %d",loop_counter);

Resources