コード例 #1
0
ファイル: gaussseidel.c プロジェクト: MatzeB/libfirm
void gs_matrix_set(gs_matrix_t *m, unsigned row, unsigned col, double val)
{
	assert(row < m->c_rows);
	assert(col < m->c_rows);
	row_col_t *the_row = &m->rows[row];

	if (row == col) {
		/* Note that we store the diagonal inverted to turn divisions to mults
		 * in matrix_gauss_seidel(). */
		assert(val != 0.0);
		the_row->diag = 1.0 / val;
		return;
	}

	/* Search for correct column */
	col_val_t *cols = the_row->cols;
	unsigned   min  = 0;
	unsigned   max  = the_row->n_cols;
	unsigned   c    = max/2;
	while (min < max) {
		unsigned idx = cols[c].col_idx;
		if (idx < col)
			min = MAX(c, min+1);
		else if (idx > col)
			max = MIN(c, max-1);
		else
			break;
		c = (min+max)/2;
	}

	/* Have we found the entry? */
	if (c < the_row->n_cols && the_row->cols[c].col_idx == col) {
		the_row->cols[c].v = val;
		if (val == 0.0)
			m->n_zero_entries++;
		return;
	}

	/* We haven't found the entry, so we must create a new one.
	 * Is there enough space? */
	if (the_row->n_cols <= the_row->c_cols)
		alloc_cols(the_row, the_row->c_cols + 16);

	/* Shift right-most entries to the right by one */
	for (unsigned i = the_row->n_cols; i > c; --i)
		the_row->cols[i] = the_row->cols[i-1];

	/* Finally insert the new entry */
	the_row->n_cols++;
	the_row->cols[c].col_idx = col;
	the_row->cols[c].v = val;

	/* Check that the entries are sorted */
	assert(c==0 || the_row->cols[c-1].col_idx < the_row->cols[c].col_idx);
	assert(c>=the_row->n_cols-1
	    || the_row->cols[c].col_idx < the_row->cols[c+1].col_idx);
}
コード例 #2
0
ファイル: gaussseidel.c プロジェクト: MatzeB/libfirm
static void alloc_rows(gs_matrix_t *m, unsigned c_rows, unsigned c_cols,
                       unsigned begin_init)
{
	assert(c_rows > m->c_rows);

	m->c_rows = c_rows;
	m->rows   = XREALLOC(m->rows, row_col_t, c_rows);

	for (unsigned i = begin_init; i < c_rows; ++i) {
		m->rows[i].c_cols = 0;
		m->rows[i].n_cols = 0;
		m->rows[i].diag   = 0.0;
		m->rows[i].cols   = NULL;
		if (c_cols > 0)
			alloc_cols(&m->rows[i], c_cols);
	}
}
コード例 #3
0
ファイル: gaussseidel.c プロジェクト: lu-zero/libfirm
static inline void alloc_rows(gs_matrix_t *m, int c_rows, int c_cols, int begin_init)
{
	int i;
	assert(c_rows > m->c_rows);

	m->c_rows = c_rows;
	m->rows   = XREALLOC(m->rows, row_col_t, c_rows);

	for (i = begin_init; i < c_rows; ++i) {
		m->rows[i].c_cols = 0;
		m->rows[i].n_cols = 0;
		m->rows[i].diag   = 0.0;
		m->rows[i].cols   = NULL;
		if (c_cols > 0)
			alloc_cols(&m->rows[i], c_cols);
	}
}
コード例 #4
0
ファイル: gaussseidel.c プロジェクト: lu-zero/libfirm
void gs_matrix_set(gs_matrix_t *m, int row, int col, double val)
{
	row_col_t *the_row;
	col_val_t *cols;
	int min, max, c, i;

	if (row >= m->c_rows) {
		int new_c_rows = (int)(ROW_INCREASE_FACTOR * row);
		alloc_rows(m, new_c_rows, m->initial_col_increase, m->c_rows);
	}

	the_row = &m->rows[row];

	if (row == col) {
		/* Note that we store the diagonal inverted to turn divisions to mults in
		 * matrix_gauss_seidel(). */
		assert(val != 0.0);
		the_row->diag = 1.0 / val;
		return;
	}

	// Search for correct column
	cols = the_row->cols;
	min  = 0;
	max  = the_row->n_cols;
	c    = max/2;
	while (min < max) {
		int idx = cols[c].col_idx;
		if (idx < col)
			min = MAX(c, min+1);
		else if (idx > col)
			max = MIN(c, max-1);
		else
			break;
		c = (max+min)/2;
	}

	// Have we found the entry?
	if (c < the_row->n_cols && the_row->cols[c].col_idx == col) {
		the_row->cols[c].v = val;
		if (val == 0.0)
			m->n_zero_entries++;
		return;
	}

	// We haven't found the entry, so we must create a new one.
	// Is there enough space?
	if (the_row->c_cols == the_row->n_cols)
		alloc_cols(the_row, the_row->c_cols + COL_INCREASE);

	// Shift right-most entries to the right by one
	for (i = the_row->n_cols; i > c; --i)
		the_row->cols[i] = the_row->cols[i-1];

	// Finally insert the new entry
	the_row->n_cols++;
	the_row->cols[c].col_idx = col;
	the_row->cols[c].v = val;

	// Check that the entries are sorted
	assert(c==0 || the_row->cols[c-1].col_idx < the_row->cols[c].col_idx);
	assert(c>=the_row->n_cols-1 || the_row->cols[c].col_idx < the_row->cols[c+1].col_idx);
}
コード例 #5
0
ファイル: gaussseidel.c プロジェクト: lu-zero/libfirm
void gs_matrix_assure_row_capacity(gs_matrix_t *m, int row, int min_capacity)
{
	row_col_t *the_row = &m->rows[row];
	if (the_row->c_cols < min_capacity)
		alloc_cols(the_row, min_capacity);
}