contributed by < ryanwang522
>
##
operator 連接字串,讓宣告更為方便。
struct command commands[] =
{
{ "quit", quit_command },
{ "help", help_command },
…
};
#define COMMAND(NAME) { #NAME, NAME ## _command }
struct command commands[] =
{
COMMAND (quit),
COMMAND (help),
…
};
所以原本 matrix.h
裡的寫法就可以替換成兩次的
typedef struct { float values[3][3]; } Mat3x3
typedef struct { float values[4][4]; } Mat4x4
#define DECLARE_MATRIX_FLEXIBLE(type, cols, rows) \
type **mat ## cols ## rows = (type **) malloc(sizeof(type *) * rows); \
for (int i = 0; i < rows; i++) \
mat ## cols ## rows[i] = (type *) malloc(sizeof(type) * cols)
DECLARE_MATRIX_FLEXIBLE(float, 4, 4);
initializer element is not constant
的編譯錯誤,參考網路上的資料應該是對全域變數進行了不合法的初始化
#define DECLARE_MATRIX_TYPE(type) \
static type **matrix_##type(int cols, int rows) { \
type **mat ## cols ## rows = (type **) malloc(sizeof(type *) * rows); \
for (int i = 0; i < rows; i++) \
mat ## cols ## rows[i] = (type *) malloc(sizeof(type) * cols); \
return mat ## cols ## rows; }
DECLARE_MATRIX_TYPE(float);
#define CREATE_MATRIX(type, cols, rows) \
type **type##_mat##cols##x##rows = matrix_##type(cols, rows)
DECLARE_MATRIX_TYPE(float)
定義可以動態配置一個二維陣列的 function,接著只要在 .c
檔呼叫 CREATE_MATRIX(float, 4, 4)
就可以產生一個 float **
型態的變數 float_mat
matrix_naive.c
的 assign
函式main()
float **alloc(int row, int col)
{
float **result;
if (!(result = (float **) malloc(row * sizeof(float *))))
return NULL;
for (int i = 0; i < col; i++)
if (!(result[i] = (float *) malloc(col * sizeof(float)))) {
free(result);
return NULL;
}
return result;
}
void free_space(float ***target, int col)
{
for (int i = 0; i < col; i++)
free((*target)[i]);
free(**target);
**target = NULL;
}
srand(time(NULL))
float randFloat(float range)
{
return ((float)rand() / (float)(RAND_MAX)) * range;
}
assign
函式如下
static void assign(Matrix *thiz, int rows, int cols, float **data)
{
thiz->row = rows;
thiz->col = cols;
thiz->priv = malloc(cols * rows * sizeof(float));
PRIV(thiz)->values = (float **) malloc(rows * sizeof(float *));
for (int i = 0; i < cols; i++)
PRIV(thiz)->values[i] = (float *) malloc(cols * sizeof(float));
for (int i = 0; i < rows; i++)
for (int j = 0; j < cols; j++)
PRIV(thiz)->values[i][j] = data[i][j];
}
thiz->priv = malloc(cols * rows * sizeof(float));
void *priv
一塊記憶體,在將 thiz->priv
cast 成 struct naive_priv *
,但不懂為什麼要給 cols * rows 的大小呢float **
,要記得 malloc 空間給她否則直接存取會造成 segmentation fault