I have experimented with my code a bit by commenting out specific parts of my code. I have found out that no segmentation fault occurs when i comment out the for loops with the variable j( shown in code). Also, when i comment out the recursive part in the function ( the lines where the function calls itself), no seg fault occurs even when the for loops are present. So clearly the for loops are causing problems in the second or higher iterations of the function, but I have no idea why. One possible reason i could think of is that infinite recursion occurs, but as far as i know no infinite recursion occurs here.
I have been trying to solve the following problem: https://www.codechef.com/problems/H1
#include<stdio.h>
int prime1[]={3,5,7,11,13,17};
int min=1000000000; //just some large number
void check(int *, int);
void swap(int*, int, int);
int prime(int);
int main()
{
int T;
scanf("%d", &T);
for(int i=0; i<T; i++)
{
printf("\n");
int arr[9];
for(int j=0; j<9; j++)
scanf("%d", &arr[j]);
check(arr, 0);
if(min==1000000000)
min=-1;
printf("%d\n", min);
}
}
void check(int arr[],int step) //step indicates the level of
//iteration
{
int k, a[9];
for(k=0; k<9; k++)
{
if(arr[k]!=k+1)
break;
}
if(k==9)
{
if(step<min)
min=step;
}
else
{
for(int i=0; i<8; i++)
{
if(i%3!=2)
{
if(prime(arr[i]+arr[i+1]))
{
for(int j=0; j<9; j++) // segmentation fault
a[j]=arr[j];
swap(a, i, i+1);
check(a, step+1);
}
}
if(i<=5)
{
if(prime(arr[i]+arr[i+3]))
{
for(int j=0; j<9; j++) // segmentation fault
a[j]=arr[j];
swap(a, i, i+3);
check(a, step+1);
}
}
}
}
}
int prime(int a)
{
for(int i=0; i<6; i++)
{
if(a==prime1[i])
return 1;
}
return 0;
}
void swap( int a[], int b, int c)
{
int temp;
temp=a[b];
a[b]=a[c];
a[c]=temp;
}
Your algorithm runs forever switching the first two tiles.
I removed some loops, i=0, k=0 and arr[] = {4,3,} we are left with:
void check(int arr[], int step)
{
int k, a[9];
// arr[0] != 1, so k != 9, we fall in else { ... }
// for (k = 0; k < 9; k++) {
// if (arr[k] != k+1)
// break;
// }
// printf("\n");
// if (k == 9) {
// if (step < min)
// min = step;
// } else {
int i = 0;
// for (int i = 0; i < 8; i++) {
// if (i%3 != 2) {
// if (prime(arr[i] + arr[i+1])) {
// i = 0, so i%3 != 2, so we fall in the first if
for (int j = 0; j < 9; j++)
a[j] = arr[j];
// you swap arr[0] with arr[1]
swap(a, i, i+1);
// and then you check again
check(a, step+1);
// and it runs so forever, never reaching this point
// }
// }
// if (i <= 5) {
// if (prime(arr[i] + arr[i+3])) {
// for (int j = 0; j < 9; j++)
// a[j] = arr[j];
// swap(a, i, i+3);
// check(a, step+1);
// }
// }
}
}
}
This algorithm needs rethinking. You need to differentiate the algorithm when run with different step number. The easiest is to switch a random title on each check, the better is to build a proper decision tree, where you remember which titles were switched.
You may interest yourself in some proper indentation,
Related
The objective: Add only the pieces of the matrix that are part of a full X (upper and lower triangle).
1 1 1
0 1 0
1 1 1
Like this, middle one should add only once.
I can't add the lower triangle properly. Help much appreciated :)
void write(int niz[20][20], int n){
int i, j;
for(i=0; i<n; i++){
for(j=0; j<n; j++){
scanf("%d", &niz[i][j]);
}
}
}
void x(int niz[20][20], int n){
//Upper triangle
int i, j, pr=n, suma=0;
for(i=0; i<n/2 + n%2; i++,pr--){
for(j=i; j<pr; j++){
suma += niz[i][j];
}
}
printf("%d\n",suma);
//Lower triangle
pr = n;
for(i=n; i>n/2 + n%2; i--,pr--){
printf("%d",pr);
for(j=n-i; j<pr; j++){
printf("\n%d", niz[i][j]);
suma += niz[i][j];
}
}
printf("%d", suma);
}
int main()
{
int n;
printf("Matrix dimensions: ");
scanf("%d", &n);
printf("Numbers in the matrix: \n");
int niz[n][n];
write(niz, n);
x(niz, n);
}
Instead of writing separate functions for each lower, upper & diagonals you can do all together with little tricks, but it works only if row == column and thats's what you want I think.
int main() {
/* it can be anything like a[3][3] or a[7][7] and elements can
be all one or all 2 or any number */
int arr[5][5] = { {1,1,1,1,1},
{0,0,1,0,0},
{0,0,1,0,0},
{0,0,1,0,0},
{1,1,1,1,1} };
int row = sizeof(arr)/sizeof(arr[0]);
int col = sizeof(arr[0])/sizeof(arr[0][0]);
int sum = 0;
for(int index = 0; index < row; index++) {
for(int sub_index = 0; sub_index < col; sub_index++) {
if(index == 0 || (index == row-1) || sub_index == row/2)
sum = sum + arr[index][sub_index];
}
}
printf("sum = %d \n",sum);
return 0;
}
Its fine if it helps you otherwise write your own logic.
There are some mismatches between the declarations and types of the arguments passed to OP's function. While in main they declare a variable length array, named niz:
int n;
// ...
int niz[n][n];
The posted signature of both write and x requires an int niz(*)[20]. It should be changed to:
void write(int n, int niz[n][n]);
// this ^^^ may be a size_t, just remember to write it before the array
About the pattern you have to follow for the sum, I can't say to fully understand your requirement, but if I'm not completely wrong, it could be done this way:
#include <stdio.h>
#include <stdlib.h>
void read_matrix(int n, int niz[n][n])
{
for(int i=0; i<n; i++) {
for(int j=0; j<n; j++) {
scanf("%d", &niz[i][j]);
}
}
}
// Separate the calculation from the printing
int hourglass_sum(int n, int niz[n][n])
{
int sum = 0;
int i = 0;
//Upper triangle
for(int k = n; i < k; ++i, --k) {
for(int j = i; j < k; ++j) {
sum += niz[i][j];
}
}
//Lower triangle
for(int k = i + 1; i < n; ++i, ++k) {
for(int j = n - i - 1; j < k; ++j) {
sum += niz[i][j];
}
}
return sum;
}
int main()
{
int n;
printf("Matrix dimensions: ");
scanf("%d", &n);
int niz[n][n];
read_matrix(n, niz);
printf("\nSum: %d", hourglass_sum(n, niz));
}
Hi there somehow my bubble sort that is suppose to work does not seem to work.Im not sure where the error is being caused.It is suppose to give me a sorted output list.It is giving me segmentation error and have been trying this for about 1 hr.Heres the code:
#include <stdio.h>
#include <stdlib.h>
#define N 10
void sort(int [], int);
void show(char *, int [], int);
int main(void)
{
int i, j, a[N];
srand(0);
for (j = 1; j <= 5; j++) {
// initialise array (pseudo-randomly)
for (i = 0; i < N; i++) {
a[i] = rand()%100;
}
// display, sort, then re-display
printf("Test #%d\n",j);
show("Sorting", a, N);
sort(a, N);
show("Sorted ", a, N);
}
return 0;
}
// sort array using bubble sort
void sort(int a[], int n)
{
int i, j, nswaps;
for (i = 0; i < n; i--) {
nswaps = 0;
for (j = n-1; j > i; j--) {
if (a[j] < a[j-1]) {
int tmp;
tmp = a[j];
a[j] = a[j-1];
a[j-1] = tmp;
nswaps++;
}
}
if (nswaps == 1) break;
}
}
// display array, preceded by label
void show(char *label, int a[], int n)
{
int i;
printf("%s:", label);
for (i = 0; i < n; i++) {
printf(" %02d", a[i]);
}
printf("\n");
}
Your are not technically sorting here.Instead of this for (i = 0; i < n; i--), try for (i = 0; i < n; i++).This is because you are starting with i=0 so in a FOR loop you need to increment i.
This problem is from spoj. Please see this for question.
My logic is simple as you will see. If I change array sizes in dynamic form to static ones, the code executes and asks for integers and keeps executing like indefinitely whilst it should run for the number of test cases. However if I have kept dynamic, I keep getting this persistent error: file_name.exe has stopped working.
Also plz comment on my code.
#include <stdio.h>
#include <conio.h>
int main()
{
int n, i, count, k, tcs, j, l, m;
scanf("%d", tcs);
int fact[tcs];
int arr[tcs];
for (j = 0; j < tcs; j++) {
scanf("%d", &arr[j]);
}
int calc_fact(n) {
if (n == 1)
return 1;
else
return n * calc_fact(n - 1);
}
j = 0;
m = 0;
while (m < tcs && j < tcs) {
fact[m] = calc_fact(arr[j]);
m++;
j++;
}
m = 0;
for (l = 0; l < tcs; l++) {
i = 1;
count = 0;
while (i <= fact[m]) {
if ((fact[m]) % i == 0)
count++;
i++;
}
m++;
k = (count) % ((10 ^ 9) + 7);
printf("\n%d", k);
}
return 0;
}
Assuming you are using C++, there are couple of things that you need to change in your code:
scanf("%d", tcs); should rather be scanf("%d", &tcs); This mistake is the reason your program crashes, as tcs doesn't have the correct intended value.
The function int calc_fact(n) should be outside the main() function with the prototype int calc_fact(int n). Due to this mistake, your code won't compile in the first place (are you sure when you say that your code complies when the arrays are declared statically)?
Please see the modified code below:
#include <stdio.h>
//#include <conio.h> //You actually don't need it.
int calc_fact(int n)
{
if(n==1)
return 1;
else
return n*calc_fact(n-1);
}
int main()
{
int n, i, count, k, tcs, j, l, m;
scanf("%d", &tcs);
int fact[tcs];
int arr[tcs];
for(j=0; j<tcs; j++)
{
scanf("%d", &arr[j]);
}
j=0;
m=0;
while(m<tcs && j<tcs)
{
fact[m]=calc_fact(arr[j]);
m++;
j++;
}
m=0;
for(l=0; l<tcs; l++)
{
i=1;
count=0;
while(i<=fact[m])
{
if((fact[m])%i==0)
count++;
i++;
}
m++;
k=(count)%((10^9)+7);
printf("%d\n", k); //and not printf("\n%d", k);
}
return 0;
}
Working code here.
I am trying to create a function that will rearrange an array so it is in descending order. The array is made up from positive integers, with no two equal elements. This is what I have:
int check (int *v, int n){
int i;
for (i=0; i<n; i++){
if (v[i] != -1){
return -1;
break;
}
else return 1;
}
}
void sortVector (int *v, int n){
int i, k, j=0, vp[n];
while (check(v,n) == -1){
for (i=0; i<n; i++){
for (k=i+1; k<n; k++){
if (v[k] > v[i]) break;
else if (k == n-1){
vp[j] = v[i];
v[i] = -1;
j++;
}
}
}
}
for (i=0; i<n; i++)
v[i] = vp[i];
}
Which is not working correctly. I've been thinking about this for the past week so some pointers would be great. Thanks.
I tried to follow the idea that you have stated in your comment by starting from your code above and made few changes and here is the two final functions
#include <stdio.h>
int check (int *v, int n)
{
int i;
for (i=0; i<n; i++)
{
if (v[i] != -1)
{
return -1; // break is useless because return has the same effect
}
}
return 1; // you need to add a return here to handle all the cases
// the case if the loop is not entered you need to return a value
}
void sortVector (int *v, int n)
{
int i, k, j=0, vp[n];
int maxIndex=0;//you need to add this variable in order to keep track of the maximum value in each iteration
while (check(v,n) == -1)
{
for (i=0; i<n; i++)
{
maxIndex=i; //you suppose that the maximum is the first element in each loop
for (k=i+1; k<n; k++)
{
if (v[k] > v[maxIndex])
maxIndex=k; // if there is another element greater you preserve its index in the variable
}
//after finishing the loop above you have the greatest variable in the array which has the index stored in maxIndex
vp[i] = v[maxIndex]; // put it in vp array
v[maxIndex]=v[i];//put it in treated elements zone
v[i]=-1;// make it -1
j++;
}
}
for (i=0; i<n; i++)
v[i] = vp[i];
}
This is the test
int main()
{
int tab[]= {1,152,24,11,9};
sortVector (tab, 5);
int i=0;
for(i=0; i<5; i++)
{
printf("%d ",tab[i]);
}
return 0;
}
which gives the desired output
152 24 11 9 1
Note: You can improve your code by making swaps on the same array instead of allocating another array !
There are really lots of algorithms for sorting. A simple algorithm is to find the minimum element in your array and put it in the first position by swapping it with whatever item was in the first position and then recursively sorting the array but this time starting at the next position.
void sort(int a[], int l, int r)
{ if(l == r) return; /* 1-elemnt array is already sorted */
int min = l;
for(int i = l+1; i <= r; i++)
{ if(a[i] < a[min])
{ min = i;
}
}
swap(a[l], a[min]);
sort(a, l+1, r);
}
You can also do it iteratively.
Perhaps, the intention like following
int check (int *v, int n){
int i;
for (i=0; i<n; i++){
if (v[i] != -1){
return -1;
//break; //This code that does not reach
}
//else return 1; //move to after for-loop
}
return 1;
}
void ordenaVetor (int *v, int n){
int i, k, j=0, vp[n];
while (check(v,n) == -1){
for (i=0; i<n; i++){
if(v[i]<0) continue;//Element of -1 excluded. v[k] too.
for (k=i+1; k<n; k++){
if (v[k]>=0 && v[i] < v[k]) break;
}
if (k == n){
vp[j] = v[i];
v[i] = -1;
j++;
break;//start over
}
}
}
for (i=0; i<n; i++){
v[i] = vp[i];
}
}
You could use an existing sort implementation instead of reinventing the wheel:
#include <stdlib.h>
int desc(void const *a, void const *b)
{
if ( *(int *)a < *(int *)b ) return 1;
return -1;
}
void sortVector (int *v, int n)
{
qsort(v, n, sizeof *v, desc);
}
I am trying to sort an array and remove duplicates.This is the function i am using in c
this code is errorfree but gives me wrong output as there are 0's in the output array. whereas there were no zeros originally
sort(int tab[], int k)
{
int temp,i,j,m;
for(i=0; i<k; i++){
for(j =i+1; j<k; j++)
{
if(tab[i] > tab[j])
{
int temp = tab[i];
tab[i]=tab[j];
tab[j]=temp;
}
else if (tab[i] == tab[j]){
for (m =j; m<k; m++){
tab[m] = tab[m+1];
}
}
}
}
}
what is the logical error in this code?I am getting 0's in my output
your code is correct... but you forgot to do a k--;
since you are removing a duplicate each time the size will decrease by 1..
sort(int tab[], int k)
{
int temp,i,j,m;
for( i=0;i<k;i++)
for( j =i+1;j<k;j++)
{
if(tab[i]>tab[j])
{
int temp = tab[i];
tab[i]=tab[j];
tab[j]=temp;
}
else if (tab[i]==tab[j])
{
for ( m =j ; m<k;m++)
tab[m]=tab[m+1];
k--;
} //end of else if
}// end of for
}