If the OrderString is ”dcfbae”, it means d > c > f > b > a > e, unlike the lexicographic(dictionary)
ordering where we have a > b > c > d > e > f.
all are lower case alphabets.
I'm getting SEG FAULT..i know its somewhat related to pointers but i'm unable to figure it out..
here's my code :
#include<stdio.h>
#include<stdlib.h>
#include<math.h>
#include<string.h>
#define MAX 1001
int min(int x,int y){
return (x>y)?y:x;
}
int check(char a,char b,char *order){
int i,x,y;
for(i=0;i<strlen(order);i++){
if(a==order[i])
x=i;
if(b==order[i])
y=i;
}
if(x>y)
return 1;
else
return 0;
}
int compare(char *a,char *b,char *order){
int i=0,l1=strlen(a),l2=strlen(b);
for(i=0;i<min(l1,l2);i++){
if(a[i]==b[i])
continue;
else{
if(check(a[i],b[i],order)==1)
return 1;
else
return 0;
}
}
}
void merge(int l,int r,int mid,char **string,char *order){
int size1=mid-l+1;
int size2=r-mid;
char a[size1][MAX],b[size2][MAX];
int i,j,k;
for(i=0;i<size1;i++)
strcpy(a[i],string[l+i]);
for(i=0;i<size2;i++)
strcpy(b[i],string[mid+1+i]);
i=0;
j=0;
k=0;
while(i<size1 && j<size2){
if(compare(a[i],b[j],order)==0){
strcpy(string[k],a[i]);
i++;
}
else{
strcpy(string[k],b[j]);
j++;
}
k++;
}
while(i<size1){
strcpy(string[k],a[i]);
i++;
k++;
}
while(j<size2){
strcpy(string[k],b[j]);
j++;
k++;
}
}
void mergesort(int l,int r,char **string,char *order){
int mid=(l+r)/2;
if(l<r){
mergesort(l,mid,string,order);
mergesort(mid+1,r,string,order);
merge(l,r,mid,string,order);
}
return ;
}
int main(){
char order[MAX];
scanf("%s",order);
int T;
scanf("%d",&T);
char string[T][MAX];
int i;
for(i=0;i<T;i++)
scanf("%s",string[i]);
mergesort(0,T-1,string,order);
for(i=0;i<T;i++)
printf("%s\n",string[i]);
return 0;
}
i'm using mergesort algorithm..
thanks in advance :)
You declare your mergesort() as follows:
void mergesort(int l,int r,char **string,char *order)
But then you invoke it as follows:
mergesort(0,T-1,string,order);
Where string is defined as follows:
char string[X][Y];
So, this is wrong: your mergesort expects a pointer to an array of pointers to char, and you are passing it an array of char.
And if your compiler is not giving you an error, or at least a warning for this, then this means that you are trying to develop software without the bare minimum warnings enabled, or you are using your compiler in some compatibility mode for some paleolithic version of C. Which is a lost cause. So, before fixing anything, before even touching your code again, figure out how to enable all warnings on your compiler, or how to get your compiler to compile for the latest C standard.
To fix this, you could either do what #kkk suggested, which tough might be a bit of work, because you'd have to fix the way your mergesort function works, or you could try to declare your string variable as follows: char** string; Then, you would have to allocate memory for it, with something like this: string = malloc( T * sizeof char* ); and then, right before reading each string, allocate each string like this: string[i] = malloc( (MAX + 1) * sizeof char ); I don't have a C compiler handy, so I can't verify that I got the syntax exactly right, but this should help you get started.
If the purpose is to avoid a crash or segfault avoid warnings first.
by the way char ** and char [][] are not different.
change this
void merge(int l,int r,int mid,char **string,char *order){
to
void merge(int l,int r,int mid,char string[][MAX],char *order){
and this
void mergesort(int l,int r,char **string,char *order){
to
void mergesort(int l,int r,char string[][MAX],char *order){
Now you'll run into not working state
Well I do not Understand your code but at least I can give you a code with no errors and you can check where is the problem in your code.
If you get wrong Answer it happens because you coded wrong.
Here is the code:
#include<stdio.h>
#include<stdlib.h>
#include<math.h>
#include<string.h>
#define MAX 1001
int min(int x,int y){
return (x>y)?y:x;
}
int check(char a,char b,char *order){
int i,x=0,y=0;
for(i=0;i<(int)strlen(order);i++){
if(a==order[i])
x=i;
if(b==order[i])
y=i;
}
if(x>y){
return 1;
}else{
return 0;
}
}
int compare(char *a,char *b,char *order){
int i=0,l1=(int)strlen(a),l2=(int)strlen(b);
for(i=0;i<min(l1,l2);i++){
if(a[i]==b[i]){
continue;
}else{
if(check(a[i],b[i],order)==1){
return 1;
}
}
}
return 0;
}
void merge(int l,int r,int mid,char string[][MAX],char *order){
int size1=mid-l+1;
int size2=r-mid;
char a[size1][MAX],b[size2][MAX];
int i,j,k;
for(i=0;i<size1;i++){
strcpy(a[i],string[l+i]);
}
for(i=0;i<size2;i++){
strcpy(b[i],string[mid+1+i]);
}
i=0;
j=0;
k=0;
printf("before :\n");
for(i=0;i<size1+size2;i++)
printf("%s\n",string[i]);
while(i<size1 && j<size2){
if(compare(a[i],b[j],order)==0){
strcpy(string[k],a[i]);
i++;
}else{
strcpy(string[k],b[j]);
j++;
}
k++;
}
while(i<size1){
strcpy(string[k],a[i]);
i++;
k++;
}
while(j<size2){
strcpy(string[k],b[j]);
j++;
k++;
}
}
void mergesort(int l,int r,char string[][MAX],char *order){
int mid=(l+r)/2;
if(l<r){
mergesort(l,mid,string,order);
mergesort(mid+1,r,string,order);
merge(l,r,mid,string,order);
}
}
int main(void){
char order[MAX];
int t,i;
if(scanf("%s",order) != 1){
exit(1);
}
if(scanf("%d",&t) != 1){
exit(1);
}
char string[t][MAX];
for(i=0;i<t;i++)
if(scanf("%s",string[i]) != 1){
exit(1);
}
mergesort(0,t-1,string,order);
return 0;
}
Output:
michi#michi-laptop:~$ ./program
acb
2
cab
bac
before :
cab
bac
Related
I got this error
*** stack smashing detected ***: terminated
Abortado (núcleo despejado)
*** stack smashing detected ***: terminated
Abortado (núcleo despejado)
when i choose a value from line 8 example like 8A or 8C.
but the function play still makes what need but when the board is printed it doesn't print line 8 like it should.
#include <stdio.h>
#include <string.h>
//void init_board(char board[8][8]){
// for(int i=0;i<8;i++){
// board[i][j]='.';
// }
// }
// board[3][3]='o';
// board[4][4]='o';
// board[3][4]='x';
// board[4][3]='x';
//}
void init_board(char board[8][8]){
for(int i=0;i<8;i++){
for(int j=0;j<8;j++){
board[i][j]='.';
}
}
board[3][3]='o';
board[4][4]='o';
board[3][4]='x';
board[4][3]='x';
board[5][2]='x';
board[5][3]='o';
board[6][1]='x';
board[3][0]='o';
board[3][1]='o';
board[4][1]='x';
board[2][5]='o';
board[2][4]='x';
}
void print_board(char board[8][8]){
printf(" A B C D E F G H");
for(int i=0;i<8;i++){
printf("\n");
printf("%d ",i+1);
for(int j=0;j<8;j++){
printf("%c ",board[i][j]);
}
}
}
int count_flips_dir(char board[8][8],int line, char col,int delta_line,int delta_col,char color){
int i;
if(board[line+delta_line][col+delta_col]=='.'){
return 0;
}
for(i=0;board[line+delta_line][col+delta_col]!=color;i++){
line=line+delta_line;
col=col+delta_col;
if(board[line+delta_line][col+delta_col]=='.'){
return 0;
}
}
return i;
}
int flanked(char board[8][8],int line,char col,char color ){
int NN = count_flips_dir(board,line,col,-1,0,color);
int ND = count_flips_dir(board,line,col,-1,1,color);
int NE = count_flips_dir(board,line,col,-1,-1,color);
int SS = count_flips_dir(board,line,col,1,0,color);
int SD = count_flips_dir(board,line,col,1,1,color);
int SE = count_flips_dir(board,line,col,1,-1,color);
int D = count_flips_dir(board,line,col,0,1,color);
int E = count_flips_dir(board,line,col,0,-1,color);
return NN+NE+ND+SD+SE+SS+E+D;
}
void changeboard(char board[8][8],int line, char col,int delta_line,int delta_col,char color){
int i;
for(i=0;board[line+delta_line][col+delta_col]!=color;i++){
board[delta_line+line][delta_col+col]=color;
line=line+delta_line;
col=col+delta_col;
}
}
void change(char board[8][8],int line,char col,char color){
if (count_flips_dir(board,line,col,-1,0,color)>0){
changeboard(board,line,col,-1,0,color);
}
if (count_flips_dir(board,line,col,-1,1,color)>0){
changeboard(board,line,col,-1,1,color);
}
if (count_flips_dir(board,line,col,-1,-1,color)>0){
changeboard(board,line,col,-1,-1,color);
}
if (count_flips_dir(board,line,col,1,0,color)>0){
changeboard(board,line,col,1,0,color);
}
if (count_flips_dir(board,line,col,1,-1,color)>0){
changeboard(board,line,col,1,-1,color);
}
if (count_flips_dir(board,line,col,1,1,color)>0){
changeboard(board,line,col,1,1,color);
}
if (count_flips_dir(board,line,col,0,1,color)>0){
changeboard(board,line,col,0,1,color);
}
if (count_flips_dir(board,line,col,0,-1,color)>0){
changeboard(board,line,col,0,-1,color);
}
}
void play(char board[8][8],int line,char col,char color){
board[line][col]=color;
change(board,line,col,color);
print_board(board);
}
int main(){
int l;
char c;
char board[8][8];
init_board(board);
print_board(board);
printf("\nEscolha a sua Jogada: ");
scanf("%d %c", &l, &c);
c=c-'A';
l=l-1;
//teste função count_flips_dir
//printf("%d",count_flips_dir(board,l,c,1,1,'o'));
//teste funçao flanked
//printf("\n%d",flanked(board,l,c,'o'));
if (board[l][c]=='.'){
if(flanked(board,l,c,'o')>0){
play(board,l,c,'o');
}
}
return 0;
}
The function change_board has an infinite loop and overwrites board cells beyond the board boundaries, causing undefined behavior, in your case corrupting stack memory.
The logic is incorrect. You should test boundary cases so delta_line+line and delta_col+col stay in the proper range [0..7] in count_flips_dir too.
I have a problem in my program which should prompt the user to enter number and the program will heapify them. The program runs but shows a runtime error after inserting the first number.
I tried to fix it multiple times but in vain.
If anyone could point to the precise error in the code it would be much appreciated. Thanks in advance. =)
Anyways, here's the code:
#include <stdio.h>
void insert_node(int arr[], int max){
if(max<15){
printf("Type the number to insert: ");
scanf("%d", arr[max]);
max++;
}
else
printf("Error. The heap is full!");
}
void printheap(int arr[], int max){
int count;
if(max>=1){
printf("\nPrinting the Heap:");
for(count==0;count<=max;count++)
printf(" %d", arr[count]);
}
}
void heapSort(int arr[], int max) {
int i=0,temp,lc,rc;
while(i!=max-1){
lc=2i+1;
rc=2i+2;
if(arr[i]<arr[lc]){
temp=arr[i];
arr[i]=arr[lc];
arr[lc]=temp;
}
else if(arr[i]<arr[rc]){
temp=arr[i];
arr[i]=arr[rc];
arr[rc]=temp;
}
i=i+1;
}
}
int main(int argc, char *argv[]){
int arr[15];
int max=0;
char ch;
while(ch!='n' && ch!='N'){
printheap(arr,max);
insert_node(arr,max);
if(max>1)
heapSort(arr,max);
printf("\nInsert another key (y:yes/n:no)? ");
scanf("%c", &ch);
}
return 0;
}
I'm learning to how to use command line arguments to get a number to decide how many elements are in an array to organize. The random number generator is supposed to take the user's number and generate that many random numbers, then sort them with the bubble sort.
But the number cannot be less than 2 or greater than 10,000.
I keep getting Segmentation fault (core dumped) or I'm able to enter any number (including a number less than 2 or greater than 10,000) and it does nothing.
I'm sure it is the first part of the code that is wrong, not the subprograms and definitions, but I don't know how to fix it.
#include <stdio.h>
int randu(void);
void bubble(int *, int);
void swap(int *, int *);
int main(int argc, char *argv[]) {
int num1;
if (argc<2) {
printf("Number must be between 2 and 10000.\n");
printf("Enter a number to sort.\n");
scanf("%d", &num1);
}
if (argc>10000) {
printf("Number must be between 2 and 10000.\n");
printf("Enter a number to sort.\n");
scanf("%d", &num1);
}
sscanf(argv[1], "%d", &num1);
int main(void) {
int x[num1], i;
for(i=0;i<num1;i++)
x[i]=randu();
printf("Here are %d numbers\n", num1);
for (i=0;i<num1;i++)
printf("%d\n",x[i]);
}
}
int randu(void) {
static int seed=17;
seed=(25179*seed+13849)%65536;
return seed;
}
void bubble(int a[], int num1){
int i,j;
for (i=0;i<num1-1;i++)
for(j=num1-1;i<j;j--)
if(a[j-1]>a[j])
swap(&a[j-1],&a[j]);
}
void swap(int *a, int *b){
int temp;
temp=*a;
*a=*b;
*b=temp;
}
There are a number of issues with your code
1) The use of argc is wrong. argc is not the value of an argument. It is the number of arguments (including program name).
2) There is a nested main inside main. Don't do that.
3) You never call the bubble sort function. Add it.
So a minor rewrite of your program:
int randu(void);
void bubble(int *, int);
void swap(int *, int *);
int main(int argc, char *argv[]) {
int num1;
if ((argc < 2) ||
(sscanf(argv[1], "%d", &num1) != 1) ||
(num1 < 2) ||
(num1 > 10000)) {
printf("You must give a number in range 2-10.000 as input\n");
return 0;
}
int x[num1], i;
for(i=0;i<num1;i++) {
x[i]=randu();
}
printf("Here are %d numbers\n", num1);
for (i=0;i<num1;i++) {
printf("%d\n",x[i]);
}
// Call the sort function
bubble(x, num1);
printf("Here are %d numbers sorted\n", num1);
for (i=0;i<num1;i++) {
printf("%d\n",x[i]);
}
return 0;
}
int randu(void) {
static int seed=17;
seed=(25179*seed+13849)%65536;
return seed;
}
void bubble(int a[], int num1){
int i,j;
for (i=0;i<num1-1;i++)
for(j=num1-1;i<j;j--)
if(a[j-1]>a[j])
swap(&a[j-1],&a[j]);
}
void swap(int *a, int *b){
int temp;
temp=*a;
*a=*b;
*b=temp;
}
"prog 5" gives the output:
Here are 5 numbers
48676
38117
52608
17049
29820
Here are 5 numbers sorted
17049
29820
38117
48676
52608
I'm 2nd year computer engineer and still in learning process of C language. I'd like to undesrtand how to dynamically alocate an array by using function instead of allocate inside the main.
Here is the code that works when I allocate array inside main.
#include <stdio.h>
#include <stdlib.h>
#include <windows.h>
#include <time.h>
#define ESC_KEY 27
#define NUM_1_KEY 49
#define NUM_2_KEY 50
void find_two_largest(int a[], int n, int *largest, int *second_largest);
void arrayInit(int *,int *, int, int);
void randGenArray(int [], int);
void inputArray(int[], int);
void result(int, int);
void loading(void);
int menu(void);
int main(void)
{
system("color f5");
int n,i,largest,largest_2, *a;
arrayInit(a,&n, 2, 10);
if(menu())
randGenArray(a,n);
else
inputArray(a,n);
find_two_largest(a,n,&largest,&largest_2);
result(largest,largest_2);
return 0;
}
void find_two_largest(int a[], int n, int *largest, int *second_largest)
{
int i=0,j=0;
system("cls");
loading();
*largest = 0;
*second_largest = *largest;
for (i=1;i<n;i++){
if(*largest<a[i])
*largest=a[i];
}
for(j=1;j<n;j++){
if(*largest==a[j])
continue;
else{
if(*second_largest<a[j])
*second_largest=a[j];
}
}
return;
}
void randGenArray(int a[], int n)
{
srand(time(NULL));
int i;
for(i=0; i<n; i++){
a[i]=rand()%100;
Sleep(10);
printf("\n>> Integer %d: %d", i+1, a[i]);
}
printf("\n\n\nPress any key to continue...");
getch();
return;
}
void inputArray(int a[], int n)
{
int i;
for(i=0; i<n; i++){
printf("\n Please enter integer %d: ", i+1);
scanf("%d",&a[i]);
}
return;
}
int menu(void)
{
char _char;
printf("\n Please choose one of the following options:\n 1.Fill array manually\n 2.Fill array by random numbers\n\n ");
while(1)
{
_char = getch();
switch(_char)
{
case ESC_KEY:
printf("\n\n Thank you for using our software!\n\n");
exit(0);
case NUM_1_KEY:
system("cls");
return 0;
case NUM_2_KEY:
system("cls");
return 1;
default:
break;
}
}
}
void arrayInit(int *a,int *n, int min, int max)
{
printf("\n Please enter a length of the array: ");
do{
scanf("%d", n);
if (*n<min||*n>max)
printf("\nThe ranged is limited. Please enter the value between %d and %d.\n", min, max);
} while(*n<min||*n>max);
a = (int*)calloc(*n,sizeof(int));
return;
}
void loading(void)
{
printf("\n Loading");
printf(".");
Sleep(300);
printf(".");
Sleep(300);
printf(".");
Sleep(300);
system("cls");
return;
}
void result(int l, int l2)
{
system("cls");
printf("\n Largest = %d Second Largest = %d",l,l2);
Sleep(500);
printf("\n\n\n Thank you using our software! ;D\n\n");
return;
}
But if you cut and paste this line from arrayInit to main and change *n to n - it will work!
a = (int*)calloc(*n,sizeof(int));
I'm sorry for asking about so stupid and obvious things but I didn't figure it out by myself. Thank you for any advice.
Here is a simple program which will show you how to do that -
#include <stdio.h>
#include <stdlib.h>
void create(int **p,int n); // function taking arguments as int ** and n is number of elements
int main(void) {
int *a;
int n=5,i; // declare and initialize n
create(&a,n); // pass address of a to function
for(i=0;i<n;i++){
a[i]=i; // store value of i in a[i]
printf("%d\n",i); // print a[i]
}
free(a); // free the allocated memory
return 0;
}
void create(int **p, int n){
*p=calloc(n,sizeof(int)); // allocate memory to *p (type- is int *)
}
Working Code
You must change your function return type
void * arrayInit(int *n, int min, int max)
{
printf("\n Please enter a length of the array: ");
do{
scanf("%d", n);
if (*n<min||*n>max)
printf("\nThe ranged is limited. Please enter the value between %d and %d.\n", min, max);
} while(*n<min||*n>max);
return calloc(*n,sizeof(int));
}
And call it from main in this way: a = arrayInit(&n, 2, 10);
i am writing multikey quicksort,i compiles fine,but when i run ,stops working abnormaly,i think it loops for ever or something like this,how could i fix this?ones again when compile no problem,here is link for it
http://ideone.com/bBtaX
it writes runtime error,here is also code
#include<stdlib.h>
#include<stdio.h>
#include<string.h>
#include<iostream>
using namespace std;
int min(int a,int b){
return a<=b?a:b;
}
#define swap(a,b){ char *t=x[a];x[a]=x[b];x[b]=t;}
#define i2c(i) x[i][depth]
void vecswap(int i, int j, int n, char *x[])
{
while (n-- > 0) {
swap(i, j);
i++;
j++;
}
}
void ssort1(char *x[],int n,int depth);
void ssort(char *x[],int n)
{
ssort1(x,n,0);
}
void ssort1(char *x[],int n,int depth){
int a,b,c,d,r,v;
if(n<=1)
return ;
a=rand()%n;
swap(0,a);
v=i2c(0);
a=b=1;
c=d=n-1;
for (;;)
{
while(b<=c && (r=i2c(b)-v)<=0){
if (r==0) {
swap(a,b);a++;
}
b++;
}
while(b<=c && (r=i2c(c)-v)>=0){
if (r==0) {
swap(c,d); d--;
}
c--;
}
if (b>c)
break;
swap(b,c);
b++;
c--;
}
r=min(a,b-a);
vecswap(0,b-r,r,x);
r = min(d-c, n-d-1);
vecswap(b, n-r, r, x);
r=b-a;
ssort1(x,r,depth);
if (i2c(r)!=0)
ssort1(x+r,a+n-d-1,depth+1);
r=d-c;
ssort1(x+n-r,r,depth);
}
int main(){
char *s[]={"dato","giorgi","beso","computer","deda","kata","spilo"};
int n=sizeof(s)/sizeof(char);
ssort(s,n);
for (int i=0;i<n;i++)
cout<<s[i]<<" "<<endl;
return 0;
}
This:
int n=sizeof(s)/sizeof(char); /* Would return 28, resulting in out of bounds
on array 's' in subsequent for loop. */
should be:
int n=sizeof(s)/sizeof(char*);
^
A safer way of determining the number of elements in an array is:
int n=sizeof(s)/sizeof(s[0]);