Firmus
Firmus

Reputation: 305

How to limit size of user inputted string or dynamically allocate memory

So I have this piece of code:

void main()
{
    char word[21]={0}; // changed from 20 to 21 because of '\0'.
    // do {
    scanf("%s", &word);
    // } while (strlen(niz)>20);  this line is useless because program crashes anyway
}
  1. Question: The thing is I want to limit the number of characters user wants to input to 20. Sure I could reserve more memory for word[] but if I went over certain number the program would crash again. How do you get around this in C?

  2. Question: Is there any way I can allocate needed memory for the string just after user enters it. For example if user enters string that has length of 999 can I allocate sizeof(string) * strlen(word) + 1 bytes of memory?

Note: if strlen() exceeds certain limit I want to prompt user to enter a new string again.

Upvotes: 2

Views: 400

Answers (5)

haccks
haccks

Reputation: 106012

You can limit the string length by using fgets:

fgets(word, sizeof(word), stdin);  

For second part:
Unfortunately, In C you can't allocate the exact amount of memory needed for the string entered. The reason is that you need to know the length of string before allocating memory for it and for this you must have to store that string in a buffer.

If you want to enter a string of any size and save memory at the same time, then use realloc.
Test program:

#include <stdio.h>
#include <stdlib.h>

int main(void)
{
    char *s = malloc(1);
    printf("Enter a string: \t"); // It can be of any length
    int c;
    int i = 0;
    do
    {
        c = getchar();
        s[i++] = c;
        s = realloc(s, i+1);
    }while(c != '\n' && c != EOF);

    s[i] = '\0';
    printf("Entered string: \t%s", s);
    return 0;
}

Upvotes: 2

K K SAI
K K SAI

Reputation: 1

Use command line arguments.. main(int argc, char *argv[ ])

Here argc will tell you how many arguments are passed when you are giving executable.

argv will give you the data or string.. Just give it to a 'char *'.

Upvotes: 0

AndersK
AndersK

Reputation: 36082

You can limit the input by using fgets instead.

fgets(word, sizeof(word), stdin);

if later need to extract things from the string use sscanf

Upvotes: 0

Piotr Praszmo
Piotr Praszmo

Reputation: 18320

Some versions of scanf support m modifier. For example in glibc>=2.7. They allocate necessary buffer for the user:

   char *p;
   int n = scanf("%ms", &p);
   if (n == 1) {
       printf("read: %s\n", p);
       free(p);
   } else {
       // error
   }

There is also older a modifier which does the same.

Upvotes: 1

Carlise
Carlise

Reputation: 126

Put a character constant in front of s in %s:

scanf("%20s", &word);

Your second question: in short No. You need memory space to take the input. A common solution however, to reduce allocations is do do something like:

char tmp[1000];
char *strptr;

scanf("%s", &temp);
strptr = malloc(sizeof(char)*(strlen(tmp)+1));

but that will only save you space if you call this function 1000s of times.

Upvotes: 0

Related Questions