static real_t aac_bits (const real_t *used_coeff, const word_t *used_states, unsigned level, const coeff_t *coeff) { real_t bits = 0; /* # bits to store coefficients */ unsigned edge; int state; word_t *counts; aac_model_t *model = (aac_model_t *) coeff->model; counts = model->counts + (1 << (1 + coeff->dc_rpf->mantissa_bits)) + ((level - coeff->min_level) * (1 << (1 + coeff->rpf->mantissa_bits))); for (edge = 0; isedge (state = used_states [edge]); edge++) if (state) bits -= log2 (counts [rtob (used_coeff [edge], coeff->rpf)] / (real_t) model->totals [level - coeff->min_level + 1]); else bits -= log2 (model->counts [rtob (used_coeff [edge], coeff->dc_rpf)] / (real_t) model->totals [0]); return bits; }
static void qac_update (const word_t *domains, const word_t *used_domains, unsigned level, int y_state, const wfa_t *wfa, void *model) { int domain; unsigned edge; bool_t used_y_state = NO; qac_model_t *qac_model = (qac_model_t *) model; bool_t y_state_is_domain = NO; if (y_state >= 0 && !usedomain (y_state, wfa)) /* don't use y-state */ y_state = -1; for (domain = 0; domain < qac_model->n; domain++) { qac_model->index [domain]++; /* mark domains unused. */ if (qac_model->states [domain] == y_state) /* match */ y_state_is_domain = YES; } for (edge = 0; isedge (domain = used_domains [edge]); edge++) if (domains [domain] == y_state) /* chroma coding */ { if (y_state_is_domain) qac_model->index [domain]--; /* undo */ qac_model->y_index >>= 1; used_y_state = YES; } else /* luminance coding */ {
static void aac_update (const real_t *used_coeff, const word_t *used_states, unsigned level, coeff_t *coeff) { unsigned edge; int state; word_t *counts; aac_model_t *model = (aac_model_t *) coeff->model; counts = model->counts + (1 << (1 + coeff->dc_rpf->mantissa_bits)) + ((level - coeff->min_level) * (1 << (1 + coeff->rpf->mantissa_bits))); for (edge = 0; isedge (state = used_states [edge]); edge++) if (state) { counts [rtob (used_coeff [edge], coeff->rpf)]++; model->totals [level - coeff->min_level + 1]++; } else { model->counts [rtob (used_coeff [edge], coeff->dc_rpf)]++; model->totals [0]++; } }
real_t compute_final_distribution (unsigned state, const wfa_t *wfa) /* * Compute the final distribution of the given 'state'. * Uses the fact that the generated 'wfa' is average preserving. * * Return value: * final distribution */ { unsigned label; real_t final = 0; for (label = 0; label < MAXLABELS; label++) { unsigned edge; int domain; if (ischild (domain = wfa->tree [state][label])) final += wfa->final_distribution [domain]; for (edge = 0; isedge (domain = wfa->into [state][label][edge]); edge++) final += wfa->weight [state][label][edge] * wfa->final_distribution [domain]; } return final / MAXLABELS; }
/* * Move to a particular position and see if we hit a mine. * If not, then count the number of mines adjacent to us so it can be seen. * If we are stepping onto a location where we remembered a mine is at, * then don't do it. Moving is only allowed to old locations, or to * locations adjacent to old ones. */ static void movetopos(POS newpos) { POS fixpos; /* position to fix up */ CELL cell; /* current cell */ GR_COUNT count; /* count of cells */ GR_COUNT i; /* index for neighbors */ if ((newpos < 0) || (newpos >= (FULLSIZE * FULLSIZE)) || !playing) return; cell = board[newpos]; if (isedge(cell) || (isseen(cell)) || isold(cell)) return; count = isold(cell); for (i = 0; i < 8; i++) if (isold(board[newpos + steptable[i]])) count++; if (count <= 0) return; cell = (cell & F_FLAGS) | F_OLD; steps++; PRINTSTEPS; if (ismine(cell)) { /* we hit a mine */ legs--; board[newpos] = (F_REMEMBER | F_MINE); cell = (F_EMPTY | F_OLD); board[newpos] = cell; drawbomb(newpos, redgc, GR_TRUE); clearcell(newpos); setcursor(); for (i = 0; i < 8; i++) { fixpos = newpos + steptable[i]; if (isold(board[fixpos])) { board[fixpos]--; drawcell(fixpos); } } drawstatus(); } count = 0; for (i = 0; i < 8; i++) if (ismine(board[newpos + steptable[i]])) count++; board[newpos] = cell | (count + '0'); drawcell(newpos); if ((legs <= 0) || (newpos == boardpos(size,size))) gameover(); }
vector<hvec> trace(hvec stpoint) /* Traces a contour. The start point, because of the way the iteration works, * is the leftmost point of the bottom line, so it starts going right. */ {hvec dir(1), left(1,1), right(0,-1); vector<hvec> contour; while (isedge(stpoint) && !ismarked(stpoint)) {contour.push_back(stpoint); mark(stpoint); if (isedge(stpoint+dir)) ; else if (isedge(stpoint+dir*left)) dir*=left; else dir*=right; stpoint+=dir; } return contour; }
word_t * compute_hits (unsigned from, unsigned to, unsigned n, const wfa_t *wfa) /* * Selects the 'n' most popular domain images of the given 'wfa'. * Consider only linear combinations of state images * {i | 'from' <= i <= 'to'}. I.e. domains are in {i | from <= i < 'to'} * Always ensure that state 0 is among selected states even though from * may be > 0. * * Return value: * pointer to array of the most popular state images * sorted by increasing state numbers and terminated by -1 */ { word_t *domains; unsigned state, label, edge; int domain; pair_t *hits = Calloc (to, sizeof (pair_t)); for (domain = 0; domain < (int) to; domain++) { hits [domain].value = domain; hits [domain].key = 0; } for (state = from; state <= to; state++) for (label = 0; label < MAXLABELS; label++) for (edge = 0; isedge (domain = wfa->into [state][label][edge]); edge++) hits [domain].key++; qsort (hits + 1, to - 1, sizeof (pair_t), sort_desc_pair); n = min (to, n); domains = Calloc (n + 1, sizeof (word_t)); for (domain = 0; domain < (int) n && (!domain || hits [domain].key); domain++) domains [domain] = hits [domain].value; if (n != domain) debug_message ("Only %d domains have been used in the luminance.", domain); n = domain; qsort (domains, n, sizeof (word_t), sort_asc_word); domains [n] = -1; Free (hits); return domains; }
static real_t uniform_bits (const real_t *used_coeff, const word_t *used_states, unsigned level, const coeff_t *coeff) { unsigned edge; real_t bits = 0; /* #bits to store coefficients */ for (edge = 0; isedge (used_states [edge]); edge++) { rpf_t *rpf = used_states [edge] ? coeff->rpf : coeff->dc_rpf; bits += rpf->mantissa_bits + 1; } return bits; }
gchar *property_helper_get_type(ScintillaObject *current_doc_sci, CXSourceLocation code_source_location) { gchar *type_string = NULL; gchar current_char, previous_char; unsigned int source_offset; size_t type_literal_begining = 0; size_t type_literal_ending = 0; gboolean is_edge = FALSE; gboolean is_in_type = FALSE; clang_getInstantiationLocation(code_source_location,NULL,NULL,NULL,&source_offset); while (is_edge == FALSE) { while (isspace((current_char = sci_get_char_at(current_doc_sci,--source_offset)))); if (current_char == ',' || current_char == '=') { while (isspace((current_char = sci_get_char_at(current_doc_sci,--source_offset)))); while (!isspace((current_char = sci_get_char_at(current_doc_sci,--source_offset)))); continue; } previous_char = sci_get_char_at(current_doc_sci,source_offset-1); if (isedge(current_char,previous_char)) { if (type_string == NULL) { if (is_in_type == FALSE) { type_string = malloc(4 * sizeof(gchar)); strncpy(type_string,"int",4); } else { gchar *untrimmed_type_string = NULL; type_literal_begining = source_offset + 1; untrimmed_type_string = sci_get_contents_range(current_doc_sci,type_literal_begining,type_literal_ending); type_string = trim_left_string(untrimmed_type_string); free (untrimmed_type_string); } is_edge = TRUE; } } if (is_in_type == FALSE) { type_literal_ending = source_offset + 1; is_in_type = TRUE; } } return type_string; }
static real_t qac_bits (const word_t *domains, const word_t *used_domains, unsigned level, int y_state, const wfa_t *wfa, const void *model) { int domain; /* counter */ real_t bits = 0; /* bit rate R */ qac_model_t *qac_model = (qac_model_t *) model; /* probability model */ if (y_state >= 0 && !usedomain (y_state, wfa)) /* don't use y-state */ y_state = -1; for (domain = 0; domain < qac_model->n; domain++) if (qac_model->states [domain] != y_state) bits += matrix_0 [qac_model->index [domain]]; if (y_state >= 0) bits += matrix_0 [qac_model->y_index]; if (used_domains != NULL) { unsigned edge; for (edge = 0; isedge (domain = used_domains [edge]); edge++) if (domains [domain] == y_state) { bits -= matrix_0 [qac_model->y_index]; bits += matrix_1 [qac_model->y_index]; } else { bits -= matrix_0 [qac_model->index [domain]]; bits += matrix_1 [qac_model->index [domain]]; } } return bits; }
real_t approximate_range (real_t max_costs, real_t price, int max_edges, int y_state, range_t *range, domain_pool_t *domain_pool, coeff_t *coeff, const wfa_t *wfa, const coding_t *c) /* * Approximate image block 'range' by matching pursuit. This functions * calls the matching pursuit algorithm several times (with different * parameters) in order to find the best approximation. Refer to function * 'matching_pursuit()' for more details about parameters. * * Return value: * approximation costs */ { mp_t mp; bool_t success = NO; /* * First approximation attempt: default matching pursuit algorithm. */ mp.exclude [0] = NO_EDGE; matching_pursuit (&mp, c->options.full_search, price, max_edges, y_state, range, domain_pool, coeff, wfa, c); /* * Next approximation attempt: remove domain block mp->indices [0] * from domain pool (vector with smallest costs) and run the * matching pursuit again. */ if (c->options.second_domain_block) { mp_t tmp_mp = mp; tmp_mp.exclude [0] = tmp_mp.indices [0]; tmp_mp.exclude [1] = NO_EDGE; matching_pursuit (&tmp_mp, c->options.full_search, price, max_edges, y_state, range, domain_pool, coeff, wfa, c); if (tmp_mp.costs < mp.costs) /* success */ { success = YES; mp = tmp_mp; } } /* * Next approximation attempt: check whether some coefficients have * been quantized to zero. Vectors causing the underflow are * removed from the domain pool and then the matching pursuit * algorithm is run again (until underflow doesn't occur anymore). */ if (c->options.check_for_underflow) { int iteration = -1; mp_t tmp_mp = mp; do { int i; iteration++; tmp_mp.exclude [iteration] = NO_EDGE; for (i = 0; isdomain (tmp_mp.indices [i]); i++) if (tmp_mp.weight [i] == 0) { tmp_mp.exclude [iteration] = tmp_mp.indices [i]; break; } if (isdomain (tmp_mp.exclude [iteration])) /* try again */ { tmp_mp.exclude [iteration + 1] = NO_EDGE; matching_pursuit (&tmp_mp, c->options.full_search, price, max_edges, y_state, range, domain_pool, coeff, wfa, c); if (tmp_mp.costs < mp.costs) /* success */ { success = YES; mp = tmp_mp; } } } while (isdomain (tmp_mp.exclude [iteration]) && iteration < MAXEDGES - 1); } /* * Next approximation attempt: check whether some coefficients have * been quantized to +/- max-value. Vectors causing the overflow are * removed from the domain pool and then the matching pursuit * algorithm is run again (until overflow doesn't occur anymore). */ if (c->options.check_for_overflow) { int iteration = -1; mp_t tmp_mp = mp; do { int i; iteration++; tmp_mp.exclude [iteration] = NO_EDGE; for (i = 0; isdomain (tmp_mp.indices [i]); i++) { rpf_t *rpf = tmp_mp.indices [i] ? coeff->rpf : coeff->dc_rpf; if (tmp_mp.weight [i] == btor (rtob (200, rpf), rpf) || tmp_mp.weight [i] == btor (rtob (-200, rpf), rpf)) { tmp_mp.exclude [iteration] = tmp_mp.indices [i]; break; } } if (isdomain (tmp_mp.exclude [iteration])) /* try again */ { tmp_mp.exclude [iteration + 1] = NO_EDGE; matching_pursuit (&tmp_mp, c->options.full_search, price, max_edges, y_state, range, domain_pool, coeff, wfa, c); if (tmp_mp.costs < mp.costs) /* success */ { success = YES; mp = tmp_mp; } } } while (isdomain (tmp_mp.exclude [iteration]) && iteration < MAXEDGES - 1); } /* * Finally, check whether the best approximation has costs * smaller than 'max_costs'. */ if (mp.costs < max_costs) { int edge; bool_t overflow = NO; bool_t underflow = NO; int new_index, old_index; new_index = 0; for (old_index = 0; isdomain (mp.indices [old_index]); old_index++) if (mp.weight [old_index] != 0) { rpf_t *rpf = mp.indices [old_index] ? coeff->rpf : coeff->dc_rpf; if (mp.weight [old_index] == btor (rtob (200, rpf), rpf) || mp.weight [old_index] == btor (rtob (-200, rpf), rpf)) overflow = YES; mp.indices [new_index] = mp.indices [old_index]; mp.into [new_index] = mp.into [old_index]; mp.weight [new_index] = mp.weight [old_index]; new_index++; } else underflow = YES; mp.indices [new_index] = NO_EDGE; mp.into [new_index] = NO_EDGE; /* * Update of probability models */ { word_t *domain_blocks = domain_pool->generate (range->level, y_state, wfa, domain_pool->model); domain_pool->update (domain_blocks, mp.indices, range->level, y_state, wfa, domain_pool->model); coeff->update (mp.weight, mp.into, range->level, coeff); Free (domain_blocks); } for (edge = 0; isedge (mp.indices [edge]); edge++) { range->into [edge] = mp.into [edge]; range->weight [edge] = mp.weight [edge]; } range->into [edge] = NO_EDGE; range->matrix_bits = mp.matrix_bits; range->weights_bits = mp.weights_bits; range->err = mp.err; } else { range->into [0] = NO_EDGE; mp.costs = MAXCOSTS; } return mp.costs; }
int main() { // Define Variables std::string parameter_filename = "solver_parms.txt"; std::string input_filename = "5x5square2.bkcfd"; std::vector<double> parameters; std::vector<double> Fiph, Fimh, Giph, Gimh; double CFL, tmax, delta_x, delta_y, min_delta_x, min_delta_y, min_delta; TDstate state_minus, state_plus, slope_minus, slope_plus, limiter_value; std::vector<TDstate> F (2); std::vector<TDstate> G (2); // double thresh = 0.00001; // 1E-5 tolerance for riemann solver - velocity double gamma = 1.4; // 1 = harmonic mean for slopes, 2 = ... int limiter_number = 1; std::vector<cell> grid; // Read parameters from input file defined by filename string parameters = read_parameters(parameter_filename); // CFL = parameters.at(0); // tmax = parameters.at(1); // Read initial file defined from Matlab with cell edges and connections // Read the initial condition file from MATLAB with [rho rho*u rho*v e] defined for each cell read_grid(input_filename, grid, gamma); std::vector<TDstate> Uph (grid.size()); min_delta_x = gridmin(grid, 'x'); min_delta_y = gridmin(grid, 'y'); min_delta = std::min(min_delta_x,min_delta_y); /* std::cout << "printing now..." << '\n'; for(auto input: grid) { std::cout << input.cellnumber << '\n'; std::cout << input.cornerlocs_x[0] << ' '; std::cout << input.cornerlocs_x[1] << ' '; std::cout << input.cornerlocs_x[2] << ' '; std::cout << input.cornerlocs_x[3] << '\n'; std::cout << input.cornerlocs_y[0] << ' '; std::cout << input.cornerlocs_y[1] << ' '; std::cout << input.cornerlocs_y[2] << ' '; std::cout << input.cornerlocs_y[3] << '\n'; std::cout << input.adjacent_cells[0] << ' '; std::cout << input.adjacent_cells[1] << ' '; std::cout << input.adjacent_cells[2] << ' '; std::cout << input.adjacent_cells[3] << '\n'; std::cout << input.state.rho << ' '; std::cout << input.state.rhou << ' '; std::cout << input.state.rhov << ' '; std::cout << input.state.E << '\n' << '\n'; } */ // Start calculation in for loop going to final time // for (double t = 0, t <= tmax; t++) double max_wavespeed = 0; // Go through each cell, calculate fluxes, update to new piecewise linear state for (unsigned int cellnum = 0; cellnum < grid.size(); ++cellnum) { // For each cell if (!isedge(grid,cellnum)) { delta_x = (vectormax(grid[cellnum].cornerlocs_x) - vectormin(grid[cellnum].cornerlocs_x)); delta_y = (vectormax(grid[cellnum].cornerlocs_y) - vectormin(grid[cellnum].cornerlocs_y)); // Calculate the limited flux of each conserved quantity for initial t -> t+1/2 update for (int direction = 0; direction < 2; ++direction) { // For the left/right direction and up/down direction // Assign the bottom/left and the top/right states for each cell assign_edge_state(state_minus, state_plus, grid, cellnum, direction); // Calculate the flux of each conserved variable, in each direction, on each face, of that cell. // Flux needs to be calculated by first finding the limiter (direction-dependent), then using that limiter to calculate the directional flux, then using the two directional fluxes to update from u_t to u_t+1/2 compute_slope(slope_minus, slope_plus, grid, cellnum, direction, state_minus, state_plus, delta_x, delta_y); compute_limiter(limiter_value, slope_minus, slope_plus, limiter_number); if (direction == 0) { // Compute F, x-fluxes compute_limited_flux(F, limiter_value, min_delta, CFL, grid[cellnum].state, slope_plus, direction, gamma); // std::cout << "rho limiter x: " << limiter_value.rho << '\n'; } else { // Compute G, y-fluxes // std::cout << "rho limiter y: " << limiter_value.rho << '\n'; compute_limited_flux(G, limiter_value, min_delta, CFL, grid[cellnum].state, slope_plus, direction, gamma); } } // end of for (int direction = 0; direction < 2; ++direction) // std::cout << "F flux: " << F[0].rho << " " << F[1].rho << ", G flux: " << G[0].rho << " " << G[1].rho << '\n'; fluxmax(max_wavespeed, F, G, grid[cellnum].state); } // end of if (!isedge(grid,cell)) // Compute the max // Now, use the fluxes calculated above to assign a new state, Uph compute_halfway_state(Uph, F, G, CFL); // ----------------------------- // Need to check values of flux to see if they are giving accurate results! // // Go through each edge, calculate flux, save // for (int edge = 1, edge <= numedges, ++edge) // // Solve riemann problem on edge for euler flux ODstate left; ODstate right; left.rho = 1.0; //rho left.rhou = 300; //rho*u or rho*v left.E = 100000/0.4 - pow(left.rhou,2)/(left.rho*2); //E right.rho = 1; right.rhou = 0; right.E = 100000/0.4 - pow(right.rhou,2)/(right.rho*2); /* ODstate test_state = Exact_Riemann_Solver(left, right, thresh, gamma); std::cout << '\n' << "State on x=0 is:" << '\n'; std::cout << test_state.rho << '\n'; std::cout << test_state.rhou << '\n'; std::cout << test_state.E << '\n'; std::cout << test_state.pressure << '\n'; */ //Use all these fluxes to define updated state on each cell //Option to save at each timestep } // end of for(unsigned int cell = 0; cell < grid.size(); ++cell) return 0; }
/** tries to find a clique, if V has only one or two nodes */ static void reduced( TCLIQUE_GETWEIGHTS((*getweights)), /**< user function to get the node weights */ TCLIQUE_ISEDGE ((*isedge)), /**< user function to check for existence of an edge */ TCLIQUE_GRAPH* tcliquegraph, /**< pointer to graph data structure */ int* V, /**< non-zero weighted nodes for branching */ int nV, /**< number of non-zero weighted nodes for branching */ TCLIQUE_WEIGHT* apbound, /**< apriori bound of nodes for branching */ int* tmpcliquenodes, /**< buffer for storing the temporary clique */ int* ntmpcliquenodes, /**< pointer to store number of nodes of the temporary clique */ TCLIQUE_WEIGHT* tmpcliqueweight /**< pointer to store weight of the temporary clique */ ) { const TCLIQUE_WEIGHT* weights; assert(getweights != NULL); assert(isedge != NULL); assert(tcliquegraph != NULL); assert(V != NULL); assert(0 <= nV && nV <= 2); assert(apbound != NULL); assert(tmpcliquenodes != NULL); assert(ntmpcliquenodes != NULL); assert(tmpcliqueweight != NULL); weights = getweights(tcliquegraph); assert(nV == 0 || weights[V[0]] > 0); assert(nV <= 1 || weights[V[1]] > 0); if( nV >= 1 ) apbound[0] = weights[V[0]]; if( nV >= 2 ) apbound[1] = weights[V[1]]; /* check if nodes are adjacent */ if( nV >= 2 && isedge(tcliquegraph, V[0], V[1]) ) { assert(isedge(tcliquegraph, V[1], V[0])); /* put nodes into clique */ tmpcliquenodes[0] = V[0]; tmpcliquenodes[1] = V[1]; *ntmpcliquenodes = 2; *tmpcliqueweight = weights[V[0]] + weights[V[1]]; apbound[0] += weights[V[1]]; } else if( nV >= 2 && weights[V[1]] > weights[V[0]] ) { /* put V[1] into clique */ tmpcliquenodes[0] = V[1]; *ntmpcliquenodes = 1; *tmpcliqueweight = weights[V[1]]; } else if( nV >= 1 ) { /* put V[0] into clique */ tmpcliquenodes[0] = V[0]; *ntmpcliquenodes = 1; *tmpcliqueweight = weights[V[0]]; } else { *tmpcliqueweight = 0; *ntmpcliquenodes = 0; } }
image_t * decode_image (unsigned orig_width, unsigned orig_height, format_e format, unsigned *dec_timer, const wfa_t *wfa) /* * Compute image which is represented by the given 'wfa'. * 'orig_width'x'orig_height' gives the resolution of the image at * coding time. Use 4:2:0 subsampling or 4:4:4 'format' for color images. * If 'dec_timer' is given, accumulate running time statistics. * * Return value: * pointer to decoded image * * Side effects: * '*dectimer' is changed if 'dectimer' != NULL. */ { unsigned root_state [3]; /* root of bintree for each band */ unsigned width, height; /* computed image size */ image_t *frame; /* regenerated frame */ word_t **images; /* pointer to array of pointers to state images */ u_word_t *offsets; /* pointer to array of state image offsets */ unsigned max_level; /* max. level of state with approx. */ unsigned state; clock_t ptimer; prg_timer (&ptimer, START); /* * Compute root of bintree for each color band */ if (wfa->wfainfo->color) { root_state [Y] = wfa->tree [wfa->tree [wfa->root_state][0]][0]; root_state [Cb] = wfa->tree [wfa->tree [wfa->root_state][0]][1]; root_state [Cr] = wfa->tree [wfa->tree [wfa->root_state][1]][0]; } else root_state [GRAY] = wfa->root_state; /* * Compute maximum level of a linear combination */ for (max_level = 0, state = wfa->basis_states; state < wfa->states; state++) if (isedge (wfa->into [state][0][0]) || isedge (wfa->into [state][1][0])) max_level = max (max_level, wfa->level_of_state [state]); /* * Allocate frame buffer for decoded image */ compute_actual_size (format == FORMAT_4_2_0 ? root_state [Y] : MAXSTATES, &width, &height, wfa); width = max (width, orig_width); height = max (height, orig_height); frame = alloc_image (width, height, wfa->wfainfo->color, format); /* * Allocate buffers for intermediate state images */ if (wfa->wfainfo->color) { wfa->level_of_state [wfa->root_state] = 128; wfa->level_of_state [wfa->tree[wfa->root_state][0]] = 128; wfa->level_of_state [wfa->tree[wfa->root_state][1]] = 128; } alloc_state_images (&images, &offsets, frame, root_state, 0, max_level, format, wfa); if (dec_timer) dec_timer [0] += prg_timer (&ptimer, STOP); /* * Decode all state images, forming the complete image. */ prg_timer (&ptimer, START); compute_state_images (max_level, images, offsets, wfa); if (dec_timer) dec_timer [1] += prg_timer (&ptimer, STOP); /* * Cleanup buffers used for intermediate state images */ prg_timer (&ptimer, START); free_state_images (max_level, frame->color, images, offsets, root_state, 0, format, wfa); /* * Crop decoded image if the image size differs. */ if (orig_width != width || orig_height != height) { frame->height = orig_height; frame->width = orig_width; if (orig_width != width) { color_e band; /* current color band */ word_t *src, *dst; /* source and destination pointers */ unsigned y; /* current row */ for (band = first_band (frame->color); band <= last_band (frame->color); band++) { src = dst = frame->pixels [band]; for (y = orig_height; y; y--) { memmove (dst, src, orig_width * sizeof (word_t)); dst += orig_width; src += width; } if (format == FORMAT_4_2_0 && band == Y) { orig_width >>= 1; orig_height >>= 1; width >>= 1; } }
void write_weights (unsigned total, const wfa_t *wfa, bitfile_t *output) /* * Traverse the transition matrices of the 'wfa' and write #'total' * weights != 0 to stream 'output'. * * No return value. */ { unsigned state, label; /* current label */ unsigned offset1, offset2; /* model offsets. */ unsigned offset3, offset4; /* model offsets. */ unsigned *weights_array; /* array of weights to encode */ unsigned *wptr; /* pointer to current weight */ unsigned *level_array; /* array of corresponding levels */ unsigned *lptr; /* pointer to current corr. level */ int min_level, max_level; /* min and max range level */ int d_min_level, d_max_level; /* min and max delta range level */ bool_t dc, d_dc; /* true if dc or delta dc are used */ bool_t delta_approx = NO; /* true if delta has been used */ unsigned delta_count = 0; /* number of delta ranges */ unsigned bits = bits_processed (output); /* * Check whether delta approximation has been used */ for (state = wfa->basis_states; state < wfa->states; state++) if (wfa->delta_state [state]) { delta_approx = YES; break; } /* * Generate array of corresponding levels (context of probability model) */ min_level = d_min_level = MAXLEVEL; max_level = d_max_level = 0; dc = d_dc = NO; for (state = wfa->basis_states; state < wfa->states; state++) for (label = 0; label < MAXLABELS; label++) if (isrange (wfa->tree [state][label])) { if (delta_approx && wfa->delta_state [state]) /* delta approx. */ { d_min_level = min (d_min_level, wfa->level_of_state [state] - 1); d_max_level = max (d_max_level, wfa->level_of_state [state] - 1); if (wfa->into [state][label][0] == 0) d_dc = YES; } else { min_level = min (min_level, wfa->level_of_state [state] - 1); max_level = max (max_level, wfa->level_of_state [state] - 1); if (wfa->into [state][label][0] == 0) dc = YES; } } if (min_level > max_level) /* no lc found */ max_level = min_level - 1; if (d_min_level > d_max_level) d_max_level = d_min_level - 1; /* * Context model: * 0 DC weight * 1 Delta DC weight * 2-k normal weights per level * k+1 - m Delta weights per level */ offset1 = dc ? 1 : 0; offset2 = offset1 + (d_dc ? 1 : 0); offset3 = offset2 + (max_level - min_level + 1); offset4 = offset3 + (d_max_level - d_min_level + 1); /* * Weights are encoded as follows: * all weights of state n * sorted by label * sorted by domain number */ wptr = weights_array = Calloc (total, sizeof (unsigned)); lptr = level_array = Calloc (total, sizeof (unsigned)); for (state = wfa->basis_states; state < wfa->states; state++) for (label = 0; label < MAXLABELS; label++) if (isrange (wfa->tree [state][label])) { int edge; /* current edge */ int domain; /* current domain (context of model) */ for (edge = 0; isedge (domain = wfa->into [state][label][edge]); edge++) { if (wptr - weights_array >= (int) total) error ("Can't write more than %d weights.", total); if (domain) /* not DC component */ { if (delta_approx && wfa->delta_state [state]) /* delta */ { *wptr++ = rtob (wfa->weight [state][label][edge], wfa->wfainfo->d_rpf); *lptr++ = offset3 + wfa->level_of_state [state] - 1 - d_min_level; delta_count++; } else { *wptr++ = rtob (wfa->weight [state][label][edge], wfa->wfainfo->rpf); *lptr++ = offset2 + wfa->level_of_state [state] - 1 - min_level; } } else /* DC component */ { if (delta_approx && wfa->delta_state [state]) /* delta */ { *wptr++ = rtob (wfa->weight [state][label][edge], wfa->wfainfo->d_dc_rpf); *lptr++ = offset1; } else { *wptr++ = rtob (wfa->weight [state][label][edge], wfa->wfainfo->dc_rpf); *lptr++ = 0; } } } } { unsigned i; unsigned *c_symbols = Calloc (offset4, sizeof (int)); const int scale = 500; /* scaling of probability model */ c_symbols [0] = 1 << (wfa->wfainfo->dc_rpf->mantissa_bits + 1); if (offset1 != offset2) c_symbols [offset1] = 1 << (wfa->wfainfo->d_dc_rpf->mantissa_bits + 1); for (i = offset2; i < offset3; i++) c_symbols [i] = 1 << (wfa->wfainfo->rpf->mantissa_bits + 1); for (; i < offset4; i++) c_symbols [i] = 1 << (wfa->wfainfo->d_rpf->mantissa_bits + 1); encode_array (output, weights_array, level_array, c_symbols, offset4, total, scale); Free (c_symbols); } debug_message ("%d delta weights out of %d.", delta_count, total); debug_message ("weights: %5d bits. (%5d symbols => %5.2f bps)", bits_processed (output) - bits, total, (bits_processed (output) - bits) / (double) total); Free (weights_array); Free (level_array); }
void compute_ip_images_state (unsigned image, unsigned address, unsigned level, unsigned n, unsigned from, const wfa_t *wfa, coding_t *c) /* * Compute the inner products between all states * 'from', ... , 'wfa->max_states' and the range images 'image' * (and childs) up to given level. * * No return value. * * Side effects: * inner product tables 'c->ip_images_states' are updated */ { if (level > c->options.images_level) { unsigned state, label; if (level > c->options.images_level + 1) /* recursive computation */ compute_ip_images_state (MAXLABELS * image + 1, address * MAXLABELS, level - 1, MAXLABELS * n, from, wfa, c); /* * Compute inner product <f, Phi_i> */ for (label = 0; label < MAXLABELS; label++) for (state = from; state < wfa->states; state++) if (need_image (state, wfa)) { unsigned edge, count; int domain; real_t *dst, *src; if (ischild (domain = wfa->tree [state][label])) { if (level > c->options.images_level + 1) { dst = c->ip_images_state [state] + image; src = c->ip_images_state [domain] + image * MAXLABELS + label + 1; for (count = n; count; count--, src += MAXLABELS) *dst++ += *src; } else { unsigned newadr = address * MAXLABELS + label; dst = c->ip_images_state [state] + image; for (count = n; count; count--, newadr += MAXLABELS) *dst++ += standard_ip_image_state (newadr, level - 1, domain, c); } } for (edge = 0; isedge (domain = wfa->into [state][label][edge]); edge++) { real_t weight = wfa->weight [state][label][edge]; if (level > c->options.images_level + 1) { dst = c->ip_images_state [state] + image; src = c->ip_images_state [domain] + image * MAXLABELS + label + 1; for (count = n; count; count--, src += MAXLABELS) *dst++ += *src * weight; } else { unsigned newadr = address * MAXLABELS + label; dst = c->ip_images_state [state] + image; for (count = n; count; count--, newadr += MAXLABELS) *dst++ += weight * standard_ip_image_state (newadr, level - 1, domain, c); } } } } }
void compute_ip_states_state (unsigned from, unsigned to, const wfa_t *wfa, coding_t *c) /* * Computes the inner products between the current state 'state1' and the * old states 0,...,'state1'-1 * * No return value. * * Side effects: * inner product tables 'c->ip_states_state' are computed. */ { unsigned level; unsigned state1, state2; /* * Compute inner product <Phi_state1, Phi_state2> */ for (level = c->options.images_level + 1; level <= c->options.lc_max_level; level++) for (state1 = from; state1 <= to; state1++) for (state2 = 0; state2 <= state1; state2++) if (need_image (state2, wfa)) { unsigned label; real_t ip = 0; for (label = 0; label < MAXLABELS; label++) { int domain1, domain2; unsigned edge1, edge2; real_t sum, weight2; if (ischild (domain1 = wfa->tree [state1][label])) { sum = 0; if (ischild (domain2 = wfa->tree [state2][label])) sum = get_ip_state_state (domain1, domain2, level - 1, c); for (edge2 = 0; isedge (domain2 = wfa->into [state2][label][edge2]); edge2++) { weight2 = wfa->weight [state2][label][edge2]; sum += weight2 * get_ip_state_state (domain1, domain2, level - 1, c); } ip += sum; } for (edge1 = 0; isedge (domain1 = wfa->into [state1][label][edge1]); edge1++) { real_t weight1 = wfa->weight [state1][label][edge1]; sum = 0; if (ischild (domain2 = wfa->tree [state2][label])) sum = get_ip_state_state (domain1, domain2, level - 1, c); for (edge2 = 0; isedge (domain2 = wfa->into [state2][label][edge2]); edge2++) { weight2 = wfa->weight [state2][label][edge2]; sum += weight2 * get_ip_state_state (domain1, domain2, level - 1, c); } ip += weight1 * sum; } } c->ip_states_state [state1][level][state2] = ip; } }
static real_t nd_prediction (real_t max_costs, real_t price, unsigned band, int y_state, range_t *range, wfa_t *wfa, coding_t *c) { real_t costs; /* current approximation costs */ range_t lrange = *range; /* * Predict 'range' with DC component approximation */ { real_t x = get_ip_image_state (range->image, range->address, range->level, 0, c); real_t y = get_ip_state_state (0, 0, range->level, c); real_t w = btor (rtob (x / y, c->coeff->dc_rpf), c->coeff->dc_rpf); word_t s [2] = {0, -1}; lrange.into [0] = 0; lrange.into [1] = NO_EDGE; lrange.weight [0] = w; lrange.mv_coord_bits = 0; lrange.mv_tree_bits = 0; lrange.nd_tree_bits = tree_bits (LEAF, lrange.level, &c->p_tree); lrange.nd_weights_bits = 0; lrange.tree_bits = 0; lrange.matrix_bits = 0; lrange.weights_bits = c->coeff->bits (&w, s, range->level, c->coeff); } costs = price * (lrange.weights_bits + lrange.nd_tree_bits); /* * Recursive aproximation of difference image */ if (costs < max_costs) { unsigned state; range_t rrange; /* range: recursive subdivision */ unsigned last_state; /* last WFA state before recursion */ real_t *ipi [MAXSTATES]; /* inner products pointers */ unsigned width = width_of_level (range->level); unsigned height = height_of_level (range->level); real_t *pixels; /* * Generate difference image original - approximation */ { unsigned n; real_t *src, *dst; /* pointers to image data */ real_t w = - lrange.weight [0] * c->images_of_state [0][0]; src = c->pixels + range->address * size_of_level (range->level); dst = c->pixels = pixels = Calloc (width * height, sizeof (real_t)); for (n = width * height; n; n--) *dst++ = *src++ + w; } /* * Approximate difference recursively. */ rrange = *range; rrange.tree_bits = 0; rrange.matrix_bits = 0; rrange.weights_bits = 0; rrange.mv_coord_bits = 0; rrange.mv_tree_bits = 0; rrange.nd_tree_bits = 0; rrange.nd_weights_bits = 0; rrange.image = 0; rrange.address = 0; last_state = wfa->states - 1; for (state = 0; state <= last_state; state++) if (need_image (state, wfa)) { ipi [state] = c->ip_images_state[state]; c->ip_images_state[state] = Calloc (size_of_tree (c->products_level), sizeof (real_t)); } compute_ip_images_state (rrange.image, rrange.address, rrange.level, 1, 0, wfa, c); costs += subdivide (max_costs - costs, band, y_state, &rrange, wfa, c, NO, YES); Free (pixels); if (costs < max_costs && ischild (rrange.tree)) /* use prediction */ { unsigned img, adr; unsigned edge; img = range->image; adr = range->address; *range = rrange; range->image = img; range->address = adr; range->nd_tree_bits += lrange.nd_tree_bits; range->nd_weights_bits += lrange.weights_bits; for (edge = 0; isedge (lrange.into [edge]); edge++) { range->into [edge] = lrange.into [edge]; range->weight [edge] = lrange.weight [edge]; } range->into [edge] = NO_EDGE; range->prediction = edge; for (state = last_state + 1; state < wfa->states; state++) if (need_image (state, wfa)) memset (c->ip_images_state [state], 0, size_of_tree (c->products_level) * sizeof (real_t)); } else costs = MAXCOSTS; for (state = 0; state <= last_state; state++) if (need_image (state, wfa)) { Free (c->ip_images_state [state]); c->ip_images_state [state] = ipi [state]; } } else costs = MAXCOSTS; return costs; }
void read_weights (unsigned total, wfa_t *wfa, bitfile_t *input) /* * Read #'total' weights from input stream 'input' and * update transitions of the WFA states with corresponding weights. * * No return value. * * Side effects: * 'wfa->weights' are filled with the decoded values */ { unsigned state; unsigned label; unsigned edge; /* current edge */ unsigned *weights_array; /* array of weights to encode */ unsigned *level_array; /* array of corresponding levels */ unsigned offset1, offset2; /* prob. model offsets. */ unsigned offset3, offset4; /* prob. model offsets. */ bool_t delta_approx = NO; /* true if delta has been used */ /* * Check whether delta approximation has been used */ for (state = wfa->basis_states; state < wfa->states; state++) if (wfa->delta_state [state]) { delta_approx = YES; break; } /* * Generate array of corresponding levels (context of probability model) */ { int min_level, max_level; /* min and max range level */ int d_min_level, d_max_level; /* min and max range level (delta) */ unsigned *lptr; /* pointer to current corresp. level */ int domain; /* current domain */ bool_t dc, d_dc; /* indicates whether DC is used */ /* * Compute minimum and maximum level of delta and normal approximations */ min_level = d_min_level = MAXLEVEL; max_level = d_max_level = 0; dc = d_dc = NO; for (state = wfa->basis_states; state < wfa->states; state++) for (label = 0; label < MAXLABELS; label++) if (isrange (wfa->tree [state][label])) { if (delta_approx && wfa->delta_state [state]) { d_min_level = min (d_min_level, wfa->level_of_state [state] - 1); d_max_level = max (d_max_level, wfa->level_of_state [state] - 1); if (wfa->into [state][label][0] == 0) d_dc = YES; } else { min_level = min (min_level, wfa->level_of_state [state] - 1); max_level = max (max_level, wfa->level_of_state [state] - 1); if (wfa->into [state][label][0] == 0) dc = YES; } } if (min_level > max_level) /* no lc found */ max_level = min_level - 1; if (d_min_level > d_max_level) d_max_level = d_min_level - 1; offset1 = dc ? 1 : 0; offset2 = offset1 + (d_dc ? 1 : 0); offset3 = offset2 + (max_level - min_level + 1); offset4 = offset3 + (d_max_level - d_min_level + 1); lptr = level_array = Calloc (total, sizeof (int)); for (state = wfa->basis_states; state < wfa->states; state++) for (label = 0; label < MAXLABELS; label++) if (isrange (wfa->tree[state][label])) for (edge = 0; isedge (domain = wfa->into[state][label][edge]); edge++) { if ((unsigned) (lptr - level_array) >= total) error ("Can't read more than %d weights.", total); if (domain) { if (delta_approx && wfa->delta_state [state]) *lptr++ = offset3 + wfa->level_of_state [state] - 1 - d_min_level; else *lptr++ = offset2 + wfa->level_of_state [state] - 1 - min_level; } else *lptr++ = delta_approx && wfa->delta_state [state] ? offset1 : 0; } } /* * Decode the list of weights with an arithmetic decoder */ { unsigned i; unsigned *c_symbols = Calloc (offset4, sizeof (unsigned)); const unsigned scale = 500; /* scaling of probability model */ c_symbols [0] = 1 << (wfa->wfainfo->dc_rpf->mantissa_bits + 1); if (offset1 != offset2) c_symbols [offset1] = 1 << (wfa->wfainfo->d_dc_rpf->mantissa_bits + 1); for (i = offset2; i < offset3; i++) c_symbols [i] = 1 << (wfa->wfainfo->rpf->mantissa_bits + 1); for (; i < offset4; i++) c_symbols [i] = 1 << (wfa->wfainfo->d_rpf->mantissa_bits + 1); weights_array = decode_array (input, level_array, c_symbols, offset4, total, scale); Free (c_symbols); } Free (level_array); /* * Update transitions with decoded weights */ { unsigned *wptr = weights_array; /* pointer to current weight */ int domain; /* current domain */ for (state = wfa->basis_states; state < wfa->states; state++) for (label = 0; label < MAXLABELS; label++) if (isrange (wfa->tree[state][label])) for (edge = 0; isedge (domain = wfa->into[state][label][edge]); edge++) { if (domain) /* not DC component */ { if (delta_approx && wfa->delta_state [state]) wfa->weight [state][label][edge] = btor (*wptr++, wfa->wfainfo->d_rpf); else wfa->weight [state][label][edge] = btor (*wptr++, wfa->wfainfo->rpf); } else { if (delta_approx && wfa->delta_state [state]) wfa->weight [state][label][edge] = btor (*wptr++, wfa->wfainfo->d_dc_rpf); else wfa->weight [state][label][edge] = btor (*wptr++, wfa->wfainfo->dc_rpf); } wfa->int_weight [state][label][edge] = wfa->weight [state][label][edge] * 512 + 0.5; } } Free (weights_array); }