This is a Matrix multiplication code. It creates a thread to multiply each row of the first matrix to the second matrix and saves the result in matrix C.
It gives an error in the pthread_create line expected primary-expression before 'void'.
I run this code on ubunto 13.10 virtual machine.
Thanks in advance.
#include <stdio.h>
#include <stdlib.h>
#include <pthread.h>
struct matrices
{
int matrixA[10][10];
int matrixB[10][10];
int matricC[10][10];
int r1,r2,c1,c2;
}*ptr;
int p;
void *matrixMul(void *);
int main()
{
int i=0,j=0;
pthread_t threads[10];
ptr=(struct matrices*)malloc(sizeof(struct matrices));
printf("Enter size of first matrix(Rows then Columns)");
scanf("%d",&(ptr->r1));
scanf("%d",&(ptr->c1));
printf("Enter elements of first array : ");
for(i=0; i<ptr->r1; i++)
{
for(j=0; j<ptr->c1; j++)
{
scanf("%d",&ptr->matrixA[i][j]);
}
}
printf("Enter size of second matrix(Rows then Columns)");
scanf("%d",&(ptr->r2));
scanf("%d",&(ptr->c2));
if(ptr->c1!=ptr->r2)
{
printf("Dimensions ERRORR! ");
}
else
{
printf("Enter elements of second array : ");
for(i=0; i<ptr->r2; i++)
{
for(j=0; j<ptr->c2; j++)
{
scanf("%d",&ptr->matrixB[i][j]);
}
}
for(i=0;i<ptr->r1;i++)
{
for(j=0;j<ptr->c2;j++)
{
ptr->matricC[i][j]=0;
}
}
for (p=0;p<ptr->r1;p++)
{
**********pthread_create(&threads[p],NULL, *matrixMul,void &p);**********
}
for(i=0;i<ptr->r1;i++)
{
pthread_join(threads[i],NULL);
}
for(i=0;i<ptr->r1;i++)
{
for(j=0;j<ptr->c2;j++)
{
printf("%d",ptr->matricC[i][j]);
}
}
}
return 0;
}
void *matrixMul(void *rownum)
{
int *i;
int n=0,m=0;
i=(int*)rownum;
for(n=0;n<ptr->c2;n++)
{
for(m=0;m<ptr->c1;m++)
{
ptr->matricC[*i][n]+=(ptr->matrixA[*i][m])*(ptr->matrixB[m][n]);
}
}
return NULL;
}
Your code contains minor error, but the logic is correct, don't worry.
I downloaded the code and tested it on my machine, so please note the following:
This line should be written this way...
pthread_create(&threads[i],NULL, matrixMul, &i);
Because according to the specs of pthread library that pthread_create should take void pointer to the runner function and void pointer to the parameter. You don't need to add (void *) because you already declared your runner function matrixMul as void *.
Your primary error here was (void) &i and it should be &i only as you already delcaired this parameter as void * in the runner function's prototype. You shall too pass the runner function like this &matrixMul.
Some other notes: "Code Review"
You shouldn't put your logic in the else statement, you can simply after printf("Dimensions ERRORR! "); write exit(-1); because this is basically what you do if the dimensions error.
Check for the return value (status) of pthread_create and pthread_join
Related
This question already has answers here:
How do I pass an array of structures to a function?
(3 answers)
Closed 1 year ago.
About to ready to give up on this
Been having an issue with my code for hours, has been telling me I have an error about the error: expected expression before 'Robot_t' and cannot find a solution, if anyone has a working solution you will save me
This is the error message provided
Arrayintofn.c: In function 'main':
Arrayintofn.c:23:23: error: expected expression before 'Robot_t'
loading_Profiles (Robot_t RobotInfo[]);
No matter what I do or who I consult there is no solution
Here is the code as well
#include <stdio.h>
#include <stdlib.h>
#include <time.h>
#include <math.h>
#include <string.h>
typedef struct
{
int Robot_Number;
char Robot_Name[30];
int Year_Manufacturer;
float Top_Speed;
float Mass;
float Best_Score;
} Robot_t;
void loading_Profiles();
int main()
{
Robot_t RobotInfo[5];
loading_Profiles (Robot_t RobotInfo[]);
int i;
for (i = 0; i < 50; i++) {
printf("%d\t\t%s\t\t%d\t\t\t%.2f\t\t%.2f\t\t%.2f\n",
RobotInfo[i].Robot_Number, RobotInfo[i].Robot_Name,
RobotInfo[i].Year_Manufacturer, RobotInfo[i].Top_Speed,
RobotInfo[i].Mass, RobotInfo[i].Best_Score);
}
return 0;
}
void loading_Profiles()
{
int Counter = 0;
int i;
Robot_t RobotInfo[5];
FILE *ROBOTtxt = fopen("Robot.txt", "r");
if (ROBOTtxt == NULL) {
perror("an error occured during the loading of the file\n");
exit(-1);
}
for (i = 0; i < 50; i++) {
char LineNumber[100] = "";
fgets(LineNumber, 100, ROBOTtxt);
sscanf(LineNumber, "%d %s %d %f %f %f",
&RobotInfo[i].Robot_Number,
RobotInfo[i].Robot_Name,
&RobotInfo[i].Year_Manufacturer,
&RobotInfo[i].Top_Speed,
&RobotInfo[i].Mass,
&RobotInfo[i].Best_Score);
Counter++;
if (feof(ROBOTtxt)) {
break;
}
}
if (ferror(ROBOTtxt)) {
perror("an error has occured");
exit(-1);
}
fclose(ROBOTtxt);
}
Your function loading_Profiles() written like this doesnt accept any parameters but you pass an array in the main function. You should rewrite the declaration as
"void loading_Profiles(Robot_t arr_name[])"
In the main function you should pass an argument only by its name. So instead of this:
"loading_Profiles(Robot_t RobotInfo[]);"
just pass:
"loading_Profiles(RobotInfo);"
There were a number of errors in your code, I'll paste my commented solution below, but for reference:
in the loading_Profiles prototype you weren't specifying a parameter
in the main, you were calling the function uncorrectly
inside the loading_Profiles implementation, you were trying to work on a local array, and not the one passed as an argument.
Also, sometimes you were using 50, sometimes 5? Which is it?
Here's the code, tested using a file generated on Mockaroo.
#include <stdio.h>
#include <stdlib.h>
#include <time.h>
#include <math.h>
#include <string.h>
typedef struct
{
int Robot_Number;
char Robot_Name[30];
int Year_Manufacturer;
float Top_Speed;
float Mass;
float Best_Score;
} Robot_t;
void loading_Profiles(Robot_t RobotInfo[]); // added parameter to prototype
int main()
{
Robot_t RobotInfo[50]; // 50 instead of 5
loading_Profiles(RobotInfo); // simply pass your variable
int i;
for (i = 0; i < 50; i++) {
printf("%d\t\t%s\t\t%d\t\t\t%.2f\t\t%.2f\t\t%.2f\n",
RobotInfo[i].Robot_Number, RobotInfo[i].Robot_Name,
RobotInfo[i].Year_Manufacturer, RobotInfo[i].Top_Speed,
RobotInfo[i].Mass, RobotInfo[i].Best_Score);
}
return 0;
}
void loading_Profiles(Robot_t RobotInfo[]) // added parameter
{
int Counter = 0;
int i;
FILE *ROBOTtxt = fopen("Robot.txt", "r");
//Robot_t RobotInfo[5]; // removed, work on the array passed as argument, not a local one
if (ROBOTtxt == NULL) {
perror("an error occured during the loading of the file\n");
exit(-1);
}
for (i = 0; i < 50; i++) {
char LineNumber[100] = "";
fgets(LineNumber, 100, ROBOTtxt);
sscanf(LineNumber, "%d %s %d %f %f %f",
&RobotInfo[i].Robot_Number,
RobotInfo[i].Robot_Name,
&RobotInfo[i].Year_Manufacturer,
&RobotInfo[i].Top_Speed,
&RobotInfo[i].Mass,
&RobotInfo[i].Best_Score);
Counter++;
if (feof(ROBOTtxt)) {
break;
}
}
if (ferror(ROBOTtxt)) {
perror("an error has occured");
exit(-1);
}
fclose(ROBOTtxt);
}
Let me know if it works
While declaring parameter for the function you need to specify variable type as structure and create an array of structure type.
void loading_Profiles(Robot_t RobotInfo[]) // added parameter
I am making a multi-threaded program to find prime numbers in C. How do I take an input in the following C program and not use (#define N =88)?
I am getting the following error:
main.c:8:7: error: expected declaration specifiers or ‘...’ before string constant
scanf("%d", &N);
^~~~
#include <stdio.h>
#include <pthread.h>
#include <conio.h>
#define MAX_THREADS 4
int N;
scanf("%d", &N);
int prime_arr[N]={0};
void *printprime(void *ptr)
{
int j,flag;
int i=(int)(long long int)ptr;
while(i<N)
{
printf("Thread id[%d] checking [%d]\n",pthread_self(),i);
flag=0;
for(j=2;j<=i/2;j++)
{
if(i%j==0)
{
flag=1;
break;
}
}
if(flag==0 && (i>1))
{
prime_arr[i]=1;
}
i+=MAX_THREADS;
}
}
int main()
{
pthread_t tid[MAX_THREADS]={{0}};
int count=0;
for(count=0;count<MAX_THREADS;count++)
{
printf("\r\n CREATING THREADS %d",count);
pthread_create(&tid[count],NULL,printprime,(void*)count);
}
printf("\n");
for(count=0;count<MAX_THREADS;count++)
{
pthread_join(tid[count],NULL);
}
int c=0;
for(count=0;count<N;count++)
if(prime_arr[count]==1)
printf("%d ",count);
return 0;
}
You can't have general statements outside of functions.
The simple solution is to read the input in the main function and then create the array in the main function as well.
And keep the array as a local variable inside the function, and pass it as an argument to the functions to call (together with its size).
To mass multiple arguments to the thread function, create a structure with the "arguments" as members, and pass a pointer to one such structure.
beginner to C here, and I am having trouble printing the words "one" in int one_three() and "two" in in the function().
the only words printing in my terminal is "starting now" - is anyone anyone aware as to why this is happening?
Any help would be very much appreciated.
int one_three();
int two();
int main(void)
{
// Countdown begins
printf("starting now: ");
printf("\n");
int one_three();
int two();
return 0;
}
int one_three()
{
printf("one");
int two();
return 0;
}
int two()
{
printf("two");
return 0;
}
You don't call the functions, you declare the functions (again).
To call e.g. one_three then you do
one_three();
And speaking about function declarations, in C you must explicitly use void as argument if a function doesn't take any arguments. A declaration such as
int two();
tells the compiler that the function two returns an int, and takes an unknown number of unspecified arguments. The proper declaration would be
int two(void);
int one_three();
int two();
int main(void)
{
// Countdown begins
printf("starting now: ");
printf("\n");
one_three();
two();
return 0;
}
int one_three()
{
printf("one");
two();
return 0;
}
int two()
{
printf("two");
return 0;
}
While calling the function you should not declare the type(ie. char, int or float).
You should change the code like this.
...
int main(void)
{
// Countdown begins
printf("starting now: ");
printf("\n");
one_three();
two();
return 0;
}
...
You have declared functions again inside main(). That's why printing only "starting now". You need to call that function from main() like this:
int main(void)
{
// Countdown begins
printf("starting now: ");
printf("\n");
one_three();
two();
return 0;
}
Let me explain you some basics.
The first two lines in your code
int one_three();
int two();
- are function declarations or function prototypes which tells the compiler that there is a function definition after the main function.
If you don't want it, you can keep the function definitions before main function.
int one_three()
{
printf("one");
int two();
return 0;
}
int two()
{
printf("two");
return 0;
}
int main(void)
{
// Countdown begins
printf("starting now: ");
printf("\n");
one_three(void);
two(void);
return 0;
}
You're re-declaring the functions again in main(), where you need to call them.
Pass a actual argument as void if you're not passing any value or reference.
Since you're returning 0 from those functions the return type is int, which will be fine.
int main(void)
{
// Countdown begins
printf("starting now: ");
printf("\n");
one_three(void);
two(void);
return 0;
}
I am trying to make multithread array sorting program in c. But when I run the program, I get an "segmentation fault" error.
Can someone help?
What should I change? First array should be 300 the other should be 500. We sort sequences separately first. After that merge 2 sorted sequences. I use "gcc -pthreads -0 soru1 soru1.c" and "./soru1" commands.
#include <stdio.h>
#include <pthread.h>
#include <stdlib.h>
#include <sys/types.h>
#include <unistd.h>
#include <time.h>
#define size 800
int orginal_dizi[size], dizi1[300], dizi2[500], dizi3[size];
int sayi,a=1;
int boyutbul(int *the)
{
int number=-1;
while(the[++number]!='\0'){}
return number;
}
void*runner(void *param)
{
int temp,i,k;
int *bolum = param;
sayi = boyutbul(bolum);
printf("\n----------unsorted %d. array-----------\n\n",a);
for(i=0; i<sayi;i++)
printf("%d\n", bolum[i]);
for(i=0; i<sayi;i++)
{
for(k=0; k<(sayi-i-1);k++)
{
if(bolum[k]>bolum[k+1])
{
temp=bolum[k];
bolum[k]=bolum[k+1];
bolum[k+1]=temp;
}
}
}
printf("\n----------sorted %d. array-----------\n\n",a);
for(i=0; i<sayi;i++)
printf("%d\n", bolum[i]);
a++;
pthread_exit(0);
}
int main()
{
pthread_t tid1,tid2, tid3;
int i=0;
while(i<size)
{
int yenisayi=1+rand()%1500;
int aynimi=0, j=0;
while(j<i)
{
if(orginal_dizi[j]==yenisayi)
{
aynimi=1;
break;
}
j++;
}
if(aynimi)
continue;
orginal_dizi[i]=yenisayi;
i++;
}
for(i=0;i<size;i++)
{
if(i<(300))
{
dizi1[i]=orginal_dizi[i];
}
else
{
dizi2[i-(500)-1]= orginal_dizi[i];
}
}
pthread_create(&tid1,NULL,runner,(void *)dizi1);
pthread_join(tid1,NULL);
pthread_create(&tid2,NULL,runner,(void *)dizi2);
pthread_join(tid2,NULL);
for(i=0; i<size;i++)
{
if(i<300)
{
dizi3[i]=dizi1[i];
}
else
{
dizi3[i]=dizi2[i-500];
}
}
pthread_create(&tid3,NULL,runner,(void *)dizi3);
pthread_join(tid3,NULL);
FILE *fp;
if((fp=fopen("son.txt","w"))== NULL)
printf("Dosya acilamadi.");
for(i=0;i<size;i++)
{
fprintf(fp, "%d\n", dizi3[i]);
}
fclose(fp);
return 0;
}
There is no multithreading in this program: every thread is immediately joined; noting runs in parallel.
The real problem is in boyutbul, which tries to figure out the length of the array by looking for '\0'. The way you initialize the arrays, there is no guarantee that they would have the terminating 0 (in fact, they wouldn't have any zeroes), so the program is doomed to access them beyond the bounds. This is UB.
I'm trying to create an array to hold an int, then when another int is to be added increase it in size to hold another int.. and so on..
I know it's not an efficient use of realloc, but it's proof on concept more than anything else. Just to get it working would allow me to optimise it and be able to apply it to something useful. A working example. The problem comes when i call the print function and it just segfaults. Any help would be appreciated.
#include <stdio.h>
#include <stdlib.h>
#include <stdbool.h>
#include <string.h>
typedef char String[100];
void begin(int *);
void add(int *, int);
void print(int *);
int tempcount=0;
int main(void)
{
int *n=NULL;
String menu;
begin(n);
while(true)
{
scanf("%9s", menu);
if(!strcmp("a", menu)) //add
{
int i=0;
scanf("%d", &i);
add(n, i);
}
else if(!strcmp("p", menu)) //print
{
print(n);
}
else if(!strcmp("q", menu)) //quit
{
free(n);
break;
}
}
return 0;
}
void begin(int *n)
{
n=malloc(sizeof(int));
if(n==NULL)
{
printf("Error in malloc!");
return;
}
n[0]=0;
printf("Added %d \n", n[0]);
}
void add(int *n, int numToAdd)
{
static int sizeCount=0;
sizeCount++;
tempcount=sizeCount;
int *temp;
temp=realloc(n, (sizeCount+1) * sizeof(int));
if(temp==NULL)
{
printf("Error in realloc!");
return;
}
n=temp;
n[sizeCount]=numToAdd;
printf("Added %d \n", n[sizeCount]);
}
void print(int *n)
{
int i;
for(i=0; i<tempcount; i++)
{
printf("%d ", n[i]);
}
}
You need to pass a pointer to your pointers in add/begin so they can modify your pointer in main
begin(&n);
...
add(&n, i);
and your definition
void begin(int **n)
{
*n=malloc(sizeof(int));
if(*n==NULL)
{
printf("Error in malloc!");
return;
}
(*n)[0]=0;
printf("Added %d \n", (*n)[0]);
}
and
void add(int **n, int numToAdd)
{
static int sizeCount=0;
sizeCount++;
tempcount=sizeCount;
int *temp;
temp=realloc(*n, (sizeCount+1) * sizeof(int));
if(temp==NULL)
{
printf("Error in realloc!");
return;
}
*n=temp;
(*n)[sizeCount]=numToAdd;
printf("Added %d \n", (*n)[sizeCount]);
}
Right now what you're doing is modifying local copies of your pointer in begin/add, so when you change it in those functions it's not modifying your pointer n in main
Also, fun fact, if you pass NULL as the first parameter to realloc it acts like a malloc, so if you initialize n to NULL, you can simply call add without first doing a begin.
Check your function add - are you sure you update the pointer value?
Try with ** as a parameter - I think it will help.