So what i'm doing is populating 2 arrays x_cord and y_cord with a maximum amount of values in each. In this case both arrays can hold a maximum amount of unique elements of 5 and each element must be between 0 and 2. Afterwards once the arrays are completely randomized I am writing the values into a file
It would look something like this:
0 0
1 2
2 1
2 2
0 1
I don't want any of the rows to be duplicates of no another, however I am running into trouble where I am creating duplicates of one another, any help would be appreciated.
Code:
for (j=0; j < num_pt; j++){
(x_cord[j] = rand()%max_x+1);
(y_cord[j] = rand()%max_y);
for(m=j+1; m < num_pt; m++){
if ((x_cord[j]==x_cord[m]) && (y_cord[j]==y_cord[m])){
x_cord[j] = rand()%max_x+1;
}
}
}
for (j=0; j < num_pt;j++){
fprintf(fp, "%d\t%d\n", x_cord[j], y_cord[j]);
}
Rather than repeatedly generating a pair until you find a unique pair, generate all pairs, then shuffle the pairs.
int max_y = 2;
int max_x = 2;
size_t num_eles = (max_x+1)*(max_y+1);
size_t desired_num_eles = 6;
if (desired_num_eles > num_eles)
desired_num_eles = num_eles;
int* y_cord = malloc(sizeof(int) * num_eles);
int* x_cord = malloc(sizeof(int) * num_eles);
for (int y = max_y; y--; ) {
for (int x = max_x; x--; ) {
size_t i = y * max_x + x;
y_cord[i] = y;
x_cord[i] = x;
}
}
for (size_t i = 0; i<desired_num_eles; ++i) {
size_t j = rand() % (num_eles - i) + i;
// Swap i and j
y_cord[i] ^= y_cord[j]; y_cord[j] ^= y_cord[i]; y_cord[i] ^= y_cord[j];
x_cord[i] ^= x_cord[j]; x_cord[j] ^= x_cord[i]; x_cord[i] ^= x_cord[j];
}
num_eles = desired_num_eles;
y_cord = realloc(sizeof(int) * num_eles);
x_cord = realloc(sizeof(int) * num_eles);
Related
I am writing a program that creates arrays of a given length and manipulates them. You cannot use other libraries.
First, an array M1 of length N is formed, after which an array M2 of length N is formed/2.
In the M1 array, the division by Pi operation is applied to each element, followed by elevation to the third power.
Then, in the M2 array, each element is alternately added to the previous one, and the tangent modulus operation is applied to the result of addition.
After that, exponentiation is applied to all elements of the M1 and M2 array with the same indexes and the resulting array is sorted by dwarf sorting.
And at the end, the sum of the sines of the elements of the M2 array is calculated, which, when divided by the minimum non-zero element of the M2 array, give an even number.
The problem is that the result X gives is -nan(ind). I can't figure out exactly where the error is.
#include <stdio.h>
#include <math.h>
#include <stdlib.h>
const int A = 441;
const double PI = 3.1415926535897931159979635;
inline void dwarf_sort(double* array, int size) {
size_t i = 1;
while (i < size) {
if (i == 0) {
i = 1;
}
if (array[i - 1] <= array[i]) {
++i;
}
else
{
long tmp = array[i];
array[i] = array[i - 1];
array[i - 1] = tmp;
--i;
}
}
}
inline double reduce(double* array, int size) {
size_t i;
double min = RAND_MAX, sum = 0;
for (i = 0; i < size; ++i) {
if (array[i] < min && array[i] != 0) {
min = array[i];
}
}
for (i = 0; i < size; ++i) {
if ((int)(array[i] / min) % 2 == 0) {
sum += sin(array[i]);
}
}
return sum;
}
int main(int argc, char* argv[])
{
int i, N, j;
double* M1 = NULL, * M2 = NULL, * M2_copy = NULL;
double X;
unsigned int seed = 0;
N = atoi(argv[1]); /* N равен первому параметру командной строки */
M1 = malloc(N * sizeof(double));
M2 = malloc(N / 2 * sizeof(double));
M2_copy = malloc(N / 2 * sizeof(double));
for (i = 0; i < 100; i++)
{
seed = i;
srand(i);
/*generate*/
for (j = 0; j < N; ++j) {
M1[j] = (rand_r(&seed) % A) + 1;
}
for (j = 0; j < N / 2; ++j) {
M2[j] = (rand_r(&seed) % (10 * A)) + 1;
}
/*map*/
for (j = 0; j < N; ++j)
{
M1[j] = pow(M1[j] / PI, 3);
}
for (j = 0; j < N / 2; ++j) {
M2_copy[j] = M2[j];
}
M2[0] = fabs(tan(M2_copy[0]));
for (j = 0; j < N / 2; ++j) {
M2[j] = fabs(tan(M2[j] + M2_copy[j]));
}
/*merge*/
for (j = 0; j < N / 2; ++j) {
M2[j] = pow(M1[j], M2[j]);
}
/*sort*/
dwarf_sort(M2, N / 2);
/*sort*/
X = reduce(M2, N / 2);
}
printf("\nN=%d.\n", N);
printf("X=%f\n", X);
return 0;
}
Knowledgeable people, does anyone see where my mistake is? I think I'm putting the wrong data types to the variables, but I still can't solve the problem.
Replace the /* merge */ part with this:
/*merge*/
for (j = 0; j < N / 2; ++j) {
printf("%f %f ", M1[j], M2[j]);
M2[j] = pow(M1[j], M2[j]);
printf("%f\n", M2[j]);
}
This will print the values and the results of the pow operation. You'll see that some of these values are huge resulting in an capacity overflow of double.
Something like pow(593419.97, 31.80) will not end well.
We have an array of "n" numbers. We need to divide it in M subarray such that the cost is minimum.
Cost = (XOR of subarray) X ( length of subarray )
Eg:
array = [11,11,11,24,26,100]
M = 3
OUTPUT => 119
Explanation:
Dividing into subarrays as = > [11] , [11,11,24,26] , [100]
As 11*1 + (11^11^24^26)*4 + 100*1 => 119 is minimum value.
Eg2: array = [12,12]
M = 1
output: 0
As [12,12] one way and (12^12)*2 = 0.
You can solve this problem by using dynamic programming.
Let's define dp[i][j]: the minimum cost for solving this problem when you only have the first i elements of the array and you want to split (partition) them into j subarrays.
dp[i][j] = cost of the last subarray plus cost of the partitioning of the other part of the given array into j-1 subarrays
This is my solution which runs in O(m * n^2):
#include <bits/stdc++.h>
using namespace std;
const int MAXN = 1000 + 10;
const int MAXM = 1000 + 10;
const long long INF = 1e18 + 10;
int n, m, a[MAXN];
long long dp[MAXN][MAXM];
int main() {
cin >> n >> m;
for (int i = 1; i <= n; i++) {
cin >> a[i];
}
// start of initialization
for (int i = 0; i <= n; i++)
for (int j = 0; j <= n; j++)
dp[i][j] = INF;
dp[0][0] = 0;
// end of initialization
for (int i = 1; i <= n; i++) {
for (int j = 1; j <= m; j++) {
int last_subarray_xor = 0, last_subarray_length = 0;
for (int k = i; k >= 1; k--) {
last_subarray_xor ^= a[k];
last_subarray_length = i - k + 1;
dp[i][j] = min(dp[i][j], dp[k - 1][j - 1] + (long long)last_subarray_xor * (long long)last_subarray_length);
}
}
}
cout << dp[n][m] << endl;
return 0;
}
Sample input:
6 3
11 11 11 24 26 100
Sample output:
119
One of the most simple classic dynamic programming problems is called "0-1 Knapsack" that's available on Wikipedia.
I am trying to find the location of a target inside of a 1-D array that acts like a table with rows and cols. I could do it using divide and mod, but I am stuck on finding it using nested loops. specifically, I can't seem to assign values inside the nested loop.
here is my code:
#include <stdio.h>
int main()
{
int arr[9] = // act as a 3 X 3 table
{ 2, 34, 6,
7, 45, 45,
35,65, 2
};
int target = 7;// r = 1; c = 0
int r = 0; // row of the target
int c = 0; // col of the target
int rows = 3;
int cols = 3;
for (int i = 0; i < rows; i++){
for (int j = 0; j + i * cols < cols + i * cols; i++ ){
if (arr[j] == target){
c = j; // columns of the target
r = i; // rows of the target
}
}
}
printf ("%d, %d",c, r);
return 0;
}
The code outputs: 0,0.
The problem isn't with the assignment, it's with the wrong loop and if condition.
The outer loop should loop over the i rows
The inner loop should loop over the j columns
within both loops, the cell to evaluate is i * cols + j
Put it all together and you'll get:
for (int i = 0; i < rows; i++) {
for (int j = 0; j < cols; j++ ) {
if (arr[i * cols + j] == target) {
c = j; // columns of the target
r = i; // rows of the target
}
}
}
Since arr is 1D array and inside for loop, for any i value j will reach upto max 3 only so its not checking after arr[3]
To avoid this problem take int pointer and points to arr and do the operation as below
int *p = arr;
for (i = 0; i < rows; i++){
for ( j = 0; j < cols ; j++ ){
if (p[j] == target){
c = j; // columns of the target
r = i; // rows of the target
}
}
p = p + j;/*make p to points to next row */
}
A better solution would use only one loop:
for (int i = 0; i < rows * cols; i++){
if (arr[i] == target){
r = i / 3;
c = i % r;
}
}
I have a matrix M of size m x n which is saved as a one dimensional array N of length m * n. Every cell of this array contains some integer variables which are the ID of data points. The amount of integer variables in every cell changes over time.
N[0] = {1,4,5,7}
N[1] = {2,9,3,1,7,4}
N[2] = {7,1,3,9,8}
N[3] = {6,4,2}
...
I access these elements by using an index function which returns
idx = x + y * n
Given some index idx I want to use all integer variables of the neighbor cells and the central cell with index idx to access an array of data points D of size s. Size s can be very large.
To make my point clear: Instead of such a loop over all data points
for(int i=0; i<s; i++)
// Do something with D[i]
I want something like (but more compact)
// Access central cell
idx = x + y*n;
num_Elements = Number_of_Elements_Cell(x,y);
for(int i=0; i<num_Elements; i++)
// Do something with D[N[idx][i]]
// Access right cell
idx = (x+1) + y*n;
num_Elements = Number_of_Elements_Cell(x+1,y);
for(int i=0; i<num_Elements; i++)
// Do something with D[N[idx][i]]
// Access left cell
idx = (x-1) + y*n;
num_Elements = Number_of_Elements_Cell(x-1,y);
for(int i=0; i<num_Elements; i++)
// Do something with D[N[idx][i]]
and so on. For all cells I have to do that 9 times.
My question: Is there a better way to do that given the structure N?
I'm not sure i understand your question well ....
but you could try :
for (int i=-1 ; i <= 1 ; i++){
for (int j = -1 ; j <=1 ; j++){
idx = (x+i) + (y+j)*n;
// Check if idx is not out of bounds
num_Elements = Number_of_Elements_Cell(x+i,y+j);
for(int k=0; k<num_Elements; k++)
// Do something with D[N[idx][k]]
}
}
Note that your index could very well be out-of-bounds which such a method, so you'll have to implement a test to prevent that.
That's the way to simply iterate on a cell and its 8 neighbors using a double for loop.
If it's not what you expect, let me know, i'll edit/delete.
I'm not sure but maybe you're looking for something like this:
var distinctDataPoints = new List<int>();
for(int z = x - 1, z <= x + 1, z++)
{
if(z < 0 || z > m)
continue;
for(int t = y-1, t <= y + 1, t++)
{
if(t < 0 || t > n)
continue;
idx = z + t * n;
for(int i = 0; i < num_Elements; i++)
{
if(!distinctDataPoints.Contains(N[idx][i])
distinctDataPoints.Add(N[idx][i])
}
}
}
for(int dpIdx = 0; dpIdx < distinctDataPoints.Count; dpIdx++)
{
//Do something with D[dpIdx]
}
I recently tried unrolling the inner i and j loops within this multi-dimensional array, but the filter->get(i,j) always messes up the texture of the image. Can anyone assist me with unrolling the i and j loop? Thanks.
My attempt:
double
applyFilter(struct Filter *filter, cs1300bmp *input, cs1300bmp *output)
{
long long cycStart, cycStop;
cycStart = rdtscll();
output -> width = input -> width;
output -> height = input -> height;
int a = filter -> getDivisor();
int n = filter -> getSize();
for (int plane = 0; plane < 3; plane++){
for(int row = 1; row < (input -> height) - 1 ; row = row + 1) {
for(int col = 1; col < (input -> width) - 1; col = col + 1) {
int value = 0;
int val1, val2;
for (int j = 0; j < n; j++) {
for (int i = 0; i < n; i+=2) {
val1 = val1 + input -> color[plane][row + i - 1][col + j - 1]
* filter -> get(i, j);
val2 = val2 + input -> color[plane][row + i][col + j -1] * filter->get(i+1,j);
}
}
value = (val1 + val2) / a;
if ( value < 0 ) { value = 0; }
if ( value > 255 ) { value = 255; }
output -> color[plane][row][col] = value;
}
}
}
cycStop = rdtscll();
double diff = cycStop - cycStart;
double diffPerPixel = diff / (output -> width * output -> height);
fprintf(stderr, "Took %f cycles to process, or %f cycles per pixel\n",
diff, diff / (output -> width * output -> height));
return diffPerPixel;
}
Original:
int a = filter -> getDivisor();
int n = filter -> getSize();
for (int plane = 0; plane < 3; plane++){
for(int row = 1; row < (input -> height) - 1 ; row = row + 1) {
for(int col = 1; col < (input -> width) - 1; col = col + 1) {
int value = 0;
for (int j = 0; j < n; j++) {
for (int i = 0; i < n; i++) {
value = value + input -> color[plane][row + i - 1][col + j - 1]
* filter -> get(i, j);
}
}
value = value / a;
if ( value < 0 ) { value = 0; }
if ( value > 255 ) { value = 255; }
output -> color[plane][row][col] = value;
Try replacing the inner loop with:
int value = 0;
int val1 = 0, val2 = 0;
for (int j = 0; j < n; j++) {
int i;
for (i = 0; i < n; i+=2) {
val1 += input->color[plane][row+i-1][col+j-1] * filter->get(i,j);
val2 += input->color[plane][row+i ][col+j-1] * filter->get(i+1,j);
}
if (i < n)
val1 += input->color[plane][row+i-1][col+j-1] * filter->get(i,j);
}
value = (val1 + val2) / a;
Your method only is correct if n is a multiple of 2. Otherwise you will miss one line.
ADDED:
First of all, I just realized that you forgot to initialize val1 and val2 which is probably the main reason for your problems.
Second, it seems to me, that your code was written specifically for filter sizes of 3:
For smaller filters you don't access the borders at all.
For bigger ones, you access positions outside of the picture, as e.g.
[row + i - 1] becomes bigger than or equal to input->height.
If you only want to use filters of size 3, then I would simply unrol the inner loops completely. Otherwise check the boundaries for the row and col values.
Now, for loop unrolling, I would recommend doing a google search, as you can find many examples on how to do that properly. One can be found on the wikipedia page.
In your case, the simplest solution would be:
int value = 0;
int val1=0, val2=0;
for (int j = 0; j < n; j++) {
for (int i = 0; i < n-1; i+=2) {
val1 = val1 + input->color[plane][row+i-1][col+j-1] * filter->get(i ,j);
val2 = val2 + input->color[plane][row+i ][col+j-1] * filter->get(i+1,j);
}
if (n%2 !=0) {
val1 = val1 + input->color[plane][row+n-2][col+j-1] * filter->get(n-1,j);
}
}
value = (val1 + val2) / a;
In case you want to unroll the loop even more, the more generic way would be (e.g. for 4):
int value = 0;
int val1=0, val2=0, val3=0, val4=0;
for (int j = 0; j < n; j++) {
for (int i = 0; i < n-3; i+=4) {
val1 = val1 + input->color[plane][row+i-1][col+j-1] * filter->get(i ,j);
val2 = val2 + input->color[plane][row+i ][col+j-1] * filter->get(i+1,j);
val3 = val3 + input->color[plane][row+i+1][col+j-1] * filter->get(i+2,j);
val4 = val4 + input->color[plane][row+i+2][col+j-1] * filter->get(i+3,j);
}
switch (n % 4) {
case 3: val1+=input->color[plane][row+n-4][col+j-1] * filter->get(i+n-3,j);
case 2: val1+=input->color[plane][row+n-3][col+j-1] * filter->get(i+n-2,j);
case 1: val1+=input->color[plane][row+n-2][col+j-1] * filter->get(i+n-1,j);
}
value = (val1 + val2 + val3 + val4) / a;
}
NOTE:
Please be aware, that depending on the size of your filter, the used compiler and compiler options and your system, the solutions above might not speed up your code but even slow it down. You should also be aware that the compiler can usually do loop unroling for you (e.g. with the -funroll-loops option in gcc) if it makes sense.