error while using array of pointers instead of 2 dimensional array - c

the following code crashes if i give array of pointer here is there any other way to accept value through array of pointers or did i do somethong wrong here
the run this program after compiling you should type
objectname -numberoflines
//program to print first n lines of string using command line arguement
#include<stdio.h>
#include<ctype.h>
#include<stdlib.h>
#include<string.h>
int less(int x,int y);`enter code here`
int main(int argc,char* argv[])
{
int i,j,n,num;
char *lines[100];/*if I use two dimensional array here the code compiles
char nu[6];
// the whole for loop is for checking error in n
for(i=1,n=strlen(argv[1]);i<n;i++)
{
if(argv[1][i]=='.')
{
printf("your input was not correct \n");
return 0;
}
if(argv[1][i]=='-')
{
printf("your input was not correct \n");
return 0;
}
if(isalpha(argv[1][i])!=0)
{
printf("your input was not correct indeed");
return 0;
}
}
printf("\t\t application to print number of last n lines \n\n\n");
printf("enter the number of lines\n");
scanf("%d",&n);
printf("enter your lines \n");
for(j=0;(n<100)&&(j<=n);j++)
{
gets(lines[j]);
}
strcpy(nu,argv[1]);
nu[0]=' ';
num=atoi(nu);
num=(less(num,n));
for(i=0;i<=num;i++)
{
printf("%s",lines[i]);
}
return 0;
}
int less(int x,int y)
{
int z;
return (z=(x>y?y,printf("your input lines are less\n"):x));
}

The main problem is that when you write
char *lines[100];
You create an array of 100 char* pointers. These pointers have no memory allocated for them and they point to a random location. Writing to that location(using gets in your program) invokes Undefined Behavior.
To fix it, allocate memory for each pointer using
for(i=0 ; i<100 ; i++)
lines[i]=malloc(AMOUNT_OF_BYTES_TO_ALLOCATE);
And later, after the use is over, free the allocated memory using
for(i=0 ; i<100 ; i++)
free(lines[i]);
The reason that it worked when you used a two dimensional array is that you create an array of array of char for which memory is automatically allocated in the stack.

Related

How to Print an array with names

I wrote this code to input names to array (eg:Jon,raj...) and the input part is ok but how to print exact name that i input to this array a[5] why this code is not working
#include <stdlib.h>
#include<stdio.h>
int main(){
int i;
char a[5];
for(i=0;i<5;i++){
printf("Enter ");
scanf("%s",&a[i]);
}
for(i=0;i<5;i++){
printf("%s \n",a[i]);
}
}
Your array a is an array of chars. This means that in each position you will have only one char.
You can do this any one of these two ways:
Pre-allocated (array of arrays of chars)
#include <stdio.h>
int main(){
const int NAME_MAXIMUM_SIZE = 50;
const int NUMBER_OF_NAMES = 5;
int index;
char names [NUMBER_OF_NAMES][NAME_MAXIMUM_SIZE];
for(index=0; index<NUMBER_OF_NAMES; index++){
printf("Enter ");
scanf("%49s",names[index]);
}
for(index=0; index<NUMBER_OF_NAMES; index++){
printf("%s \n",names[index]);
}
}
Malloc + free (array of pointers)
#include <stdio.h>
#include <stdlib.h>
int main(){
const int NAME_MAXIMUM_SIZE = 50;
const int NUMBER_OF_NAMES = 5;
int index;
char *names [NUMBER_OF_NAMES];
for(index=0; index<NUMBER_OF_NAMES; index++){
names[index] = (char*)malloc(NAME_MAXIMUM_SIZE);
printf("Enter ");
scanf("%49s",names[index]);
}
for(index=0; index<NUMBER_OF_NAMES; index++){
printf("%s \n",names[index]);
free(names[index]);
}
}
You can make use of 2 dimensional array. Here your variable a which is a character array stores only one character at each index.
#include <stdlib.h>
#include<stdio.h>
int main(){
int i;
char a[5];
for(i=0;i<5;i++){
printf("Enter ");
scanf("%s",&a[i]);
}
for(i=0;i<5;i++){
printf("%s \n",a[i]);
}
}
"...wrote this code to input names to array..."
char a[5] does not create 5 C strings. It is simply an array of 5 char. It provides room for only 1, 4 character C string (leaving room for the \0 terminator). If you need an array of names, of typical size the code will need an array of arrays each with space sufficient for typical names. For example:
char a[5][80] = {{0}}; //provides an array capable of containing 5 names
Also, in the read statement: scanf("%s",&a[i]);, the format code %s is expecting to process an array of char. But is provided with &a[i] which is only a single character. If you are going to use scanf, then call it like this: scanf("%s",a); Same issue with the print statement.
Make the following edits to address these basic issues:
int main(void)
{
int i = 0;
char a[5][80] = {{0}};//space for 5 names, each with up to 79 characters
//arrays are initialized to zeros
for(i=0;i<sizeof(a)/sizeof(a[0]);i++)//sizeof(a)/sizeof(a[0]) is flexible way to
//loop only through number of names.
//If array size changes, expression will still work
{
printf("Enter name %d:\n ", i+1);
scanf("%79s",a[i]);//limit input to prevent overflow
// ^^
}
for(i=0;i<sizeof(a[0])/sizeof(a[0][0]);i++)
{
printf("%s \n",a[i]);
}
return 0;
}

How initialize array dynamically using function in C

SS4SS of 3rd Problem
I want to create the program to take the input from user until he presses 1.
I'm using dynamic memory allocation using function and after running this code, this program takes only 4 input and it does not show any output
output
#include <stdio.h>
#include <stdlib.h>
#include <limits.h>
void input(int **arr)
{
int n=1,i=0;
*arr=(int *)malloc(sizeof(int));
int ch;
do
{
printf("\nEnter '1' To Enter A Value in array or else enter '0'");
scanf("%d",&ch);
if (ch==1)
{
if (!*arr)
{
printf("\nInsufficient Memory!");
return;
}
printf("\nEnter the value\t:\t");
scanf("%d", arr[i]);
*arr=realloc(*arr,sizeof(int)*(++n));
*arr[++i]=INT_MIN;
}
else if (ch!=1&&ch!=0)
{
printf("\nInvalid input!");
continue;
}
} while(ch!=0);
free(arr);
}
void display(int **arr)
{
for (int i = 0; i < 3; i++)
printf("\n%d", **(arr+i));
free(arr);
}
int main()
{
int *arr;
input(&arr);
display(&arr);
free(arr);
return 0;
}
First question
With !*arr[i] you are checking the logical value contained in *arr[i], which can have a random value before you assign a value to it. In your case, the value contained in *arr[i] is 0, triggering the condition !*arr[i].
The correct way of checking if realoc() was succesful, is checkin it's returned value. If it's null, the request failed. In your case, it would be replacing
if(!*arr[i])
by
if(!*arr)
Second question
In this line *arr[++i]=INT_MIN; the index [] operator has precedence over pointer * operator. You have to write parenthesis:
(*arr)[++i]=INT_MIN;
And also here
scanf("%d", arr[i]);
you are saying that arr is an array, when it is a pointer to an array. You should replace it with:
scanf("%d", *arr + i);
Third question
You are also doing free() before you access the values in the array, which triggers the error. You should remove the free() calls at the end of input() and display() and leave only the one of the end of main().
You have still to replace the printf() in display with
printf("\n%d", (*arr)[i]));

Pass array to function (C)

I've written a function to rotate an array,
I've checked and it works when code is in one block I.E. everything
is coded under main(), but when I divide the code so that the rotation is done under a different function I can't get it to work (it truncates instead of rotating).
I'm pretty sure it's something to do with the array pointer.
sorry complete noob
please help:
#include<stdio.h>
void rotate(int *arr,int length);
int main()
{
// this code creates an array via input
int length;
int i;
int num;
printf("enter length of array\n");
scanf("%d",&length);
int arr[length];
for (i=0;i<length;i++) {
printf("enter number\n");
scanf("%d",&num);
arr[i]=num;
}
// just prints original
for(i=0;i<length;i++){
printf("original arr[%d]=%d\n",i,arr[i]);
}
//runs rotate function
rotate(arr,length);
return 0;
}
//the rotate function inputs rotation amount and uses nested for loop to
execute
void rotate(int *arr,int length)
{
int n;
printf("by how many do you want to rotate array?");
scanf("%d",&n);
int i;
int j;
int temp;
for (j=0;j<n;j++)
{
temp=arr[0];
for (i=0;i<length-1;i++)
{
arr[i]=arr[i+1];
}
arr[length-1]=temp;
printf("rotated arr[%d] = %d\n",i,arr[i]);
}
}
my output looks like this:
enter length of array
5
enter number
1
enter number
2
enter number
3
enter number
4
enter number
5
original arr[0]=1
original arr[1]=2
original arr[2]=3
original arr[3]=4
original arr[4]=5
by how many do you want to rotate array?
3
rotated arr[4] = 1
rotated arr[4] = 2
rotated arr[4] = 3
RUN FINISHED; exit value 0; real time: 9s; user: 0ms; system: 0ms
In C you need to declare the function before "main" function, or do the declaration and definition both above the main function. Also do share your error message, for help.
Also, in C language you can't really create dynamic arrays like that( i.e. taking an integer value and then defining the size of array using it "int array[integer] " is wrong of doing it, if the value of integer is being given during runtime)
Read http://www.mathcs.emory.edu/~cheung/Courses/255/Syllabus/2-C-adv-data/dyn-array.html , or any other tutorial about dynamic arrays in C and how to use malloc and calloc.
According to me the problem is in your last print statement in rotate method which is inside the loop.
you must loop through the whole array again to print the rotated array.
like this.
void rotate(int *arr,int length)
{
int n;
printf("by how many do you want to rotate array?");
scanf("%d",&n);
int i;
int j;
int temp;
for (j=0;j<n;j++)
{
temp=arr[0];
for (i=0;i<length-1;i++)
{
arr[i]=arr[i+1];
}
arr[length-1]=temp;
}
for(i=0;i<length;i++){
printf("original arr[%d]=%d\n",i,arr[i]);
}
}
this will work.
And also, Always define functions at the top in c.

How to make array 1*x and sum up its digits?

So i have this type of problem. How to make an array 1*x and then sum up its digits together. I wrote down something like this for now. Any ideas? Thank you.
#include <stdio.h>
#include <stdlib.h>
#include <math.h>
/* run this program using the console pauser or add your own getch, system("pause") or input loop */
int main(int argc, char *argv[])
{
int a,i,w,j,m;
int s[a];
printf("How many digits do you want to sum up\n");
scanf("%d",&a);
for(i=0;i<a;i++)
{
printf("Enter numer %d: ",i);
scanf("%d",&s[i]);
}
for(j=0;j<a;j++)
{
m=s[j]+s[j++];
}
printf("\n %d",m);
return 0;
}
The problems of your code are:
int a;
int s[a];
Here a is uninitialized.So,array size is unknown which is incorrect.And,instead of this
m=s[j]+s[j++];
you should do like this :
m += s[j];
One more thing,you have initialize m = 0 before starting to add.
I've Changed your program to this:
#include <stdio.h>
int main(int argc, char *argv[]) {
int a,i,m = 0;
//First get the array size
printf("How many digits do you want to sum up\n");
scanf("%d",&a);
//Then declare the array with the size (a)
int s[a];
for(i = 0; i < a; i++){
printf("Enter numer %d: ",i);
scanf("%d",&s[i]);
m += s[i];
}
printf("\n %d",m);
return 0;
}
Using uninitialized variable is undefined behaviour.
int s[a];
The above statement defines an array s of size a but the value of a is unpredictable since it is uninitialized and contains garbage. The size of the array must be known when it defined and it remains the same throughout its lifetime. You cannot resize your array by changing the value of a here. You can use dynamic memory allocation using malloc.
Further, the following statement again invokes undefined behaviour -
m=s[j]+s[j++];
That's because it violates the the following rule stated in the C99 standard §6.5 ¶2
Between the previous and next sequence point an object shall have its
stored value modified at most once by the evaluation of an expression.
Furthermore, the prior value shall be read only to determine the value
to be stored.

Two Dimensional Array of Characters in C

Help me to get out of this problem. I'm using GCC on ubuntu12.04. While I write this program to get 5 strings from keyboard n then print these strings on screen. Program is compiled but during execution it takes strings from keyboard but print only last string. The program which I have written is below:
void main()
{
char names[10];
int i,j;
for(i=0;i<5;i++)
{
printf(" Enter a name which you want to register\n");
scanf("%s",names);
}
for(i=0;i<5;i++)
printf(" the names you enter are %s\n", names);
}
1) you can use 2D char array in this way
char names[5][100];
each line in the 2D array is an array of char with size = 100
for(i=0;i<5;i++)
{
printf(" Enter a name which you want to register\n");
scanf("%99s",names[i]);
}
2) You can use array of pointers in this way
char *names[5];
each element in the array is a pointer to a string (char array). you have to assign each pointer in the array to a memory space before you call scanf()
for(i=0;i<5;i++)
{
names[i]=malloc(100);
printf(" Enter a name which you want to register\n");
scanf("%99s",names[i]);
}
3) if you compile with gcc version >2.7 then your scanf() can allocate memory by using "%ms" instead of "%s"
char *names[5];
for(i=0;i<5;i++)
{
printf(" Enter a name which you want to register\n");
scanf("%ms",&names[i]);
}
There is a simple example about reading and keeping string in the char array.
#include <stdio.h>
const int MACRO = 6;
int main() {
printf("Hello Admin Please Enter the Items:\n");
char items[MACRO][20];
for (int i = 0; i < MACRO; ++i) {
scanf("%19s", items[i]);
}
for (int i = 0; i < MACRO; ++i) {
printf("%s ", items[i]);
}
return 0;
}
In your program the mistake is that you have not putted '&'address of operator int the first for loop . names in your case is an array if you store %s string in names and not &names[0] or &names[1] or so on then as array itself acts as a pointer therefore the array "names" is pointing to the address of its first elements i.e. names[0] . so if you are writing scanf("%s",names); that is similar to scanf("%s",&names[0]); so as you are storing the names in one element only and that too for 5 iterations for only the last string you have entered will be stored and previous strings will be gone . so onlye last string is printed in your program .
in your code, you only declare char data type to be one dimensional and thus it will always overwrite the previous input,that's why the result is the last input printed 5 times.
char names[10];
the above declaration means that you declare a char type variable only with 10 character size without an extra array,it means you only declare a single variable for 5 input.
to make a two dimensional char, you will need to declare it like this :
char names[5][10];
in the code above, it means that you declare a char type variable with 10 character size in an array of 5.
Here is the code I wrote using pointer.
#include <stdio.h>
void main()
{
char *string[100];
int ln;
printf("Enter numbar of lines: ");
scanf("%d",&ln);
printf("\n");
for(int x=0;x<ln;x++)
{
printf("Enter line no - %d ",(x+1));
scanf("%ms",&string[x]); // I am using gcc to compile file, that's why using %ms to allocate memory.
}
printf("\n\n");
for(int x=0;x<ln;x++)
{
printf("Line No %d - %s \n",(x+1),string[x]);
}
}
Another code using two dimensional Array
#include <stdio.h>
void main()
{
int ln;
printf("Enter numbar of lines: ");
scanf("%d",&ln);
printf("\n");
char string[ln][10];
for(int x=0;x<ln;x++){
printf("Enter line no - %d ",(x+1));
scanf("%s",&string[x][0]);
}
for(int x=0;x<ln;x++)
{
printf("Line No %d - %s \n",(x+1),string[x]);
}
}

Resources