-5

I have written a program to find the longest word and to print it.

My code is:

#include <stdio.h>
#include <string.h>
#include <ctype.h>

int MaxWord(char text[],char[]);

int main (void){
  char text[1000];
  char word[1000];
  int max;

  printf("geben Sie den Text bitte : ");
  gets(text);
  max=MaxWord(text,word);
  printf("ist mit %d Zeichen das laengste wort im Text\n\n\n",max);
  return 0;
}
int MaxWord(char text[], char word[])
{
  char i;
  int ctr=0;
  int max=0;
  int len;
  char begin=0;

  len=strlen(text);
  for(i=0;i<len+1;i++)
  {
    if(isalpha(text[i]))
    {
        if(ctr==0)
        {
            begin=i;
        }
        ctr++;
    }
    else 
    {

        if(ctr>max)
        {
            max=ctr;

        }

        ctr=0;
    }
 }
 strncpy(word,begin,max);
 printf("%s ",word);
 return max;
}   

and the error is:

error #2140: Type error in argument 2 to 'strncpy'; expected 'const char * restrict' but found 'char'.

How can I fix this?

phoenix
  • 3,069
  • 3
  • 22
  • 29
  • 3
    Don't use `gets`. Just starting out in C isn't a reasonable excuse for doing so. – John Coleman Dec 01 '15 at 20:53
  • @JohnColeman While true, `gets` is not related to the problem here. – user253751 Dec 01 '15 at 20:53
  • 6
    read the error message? strncpy is expecting a pointer, and you passed in a char. – Marc B Dec 01 '15 at 20:55
  • 1
    `strncpy()` expects its second argument to be a pointer to the source string. You are passing a `char` instead. Pass what it expects -- possibly something like `text + begin`. – John Bollinger Dec 01 '15 at 20:55
  • 4
    @immibis I didn't say it was -- but I think that it is a civic duty to object to `gets` whenever it appears in code on Stack Overflow. – John Coleman Dec 01 '15 at 20:55
  • @JohnColeman i have to use gets for the strings and scanf can not solve the problem –  Dec 01 '15 at 20:55
  • @MahmoudAbosaleh `fgets` *can* solve the problem without risking buffer overflow. – John Coleman Dec 01 '15 at 20:56
  • 1
    Note also that type `char` likely is too narrow to index every element of a 1000-element array. On most systems it is only 8 bits wide, and on many it is signed, so it may not be able to index more than 127 positions. You probably want `begin` to be an `int` or `unsigned int` instead. – John Bollinger Dec 01 '15 at 20:57
  • @MahmoudAbosaleh your wrong assumption is that `scanf` is the only alternate to `gets` – bolov Dec 01 '15 at 20:57
  • note that `strncpy` does not set the NULL character in this case. – BLUEPIXY Dec 01 '15 at 21:00

2 Answers2

1

Firstly you should not be using gets() function. Use scanf instead. Also see http://www.cplusplus.com/reference/cstring/strncpy/

The function strncpy expects a const char* ( so that you are assured the function will not modify the source string ) and you are passing it a char. Hence the error. Please modify your function to pass in a char pointer.

You would need to recheck your logic and fix your strncpy call by passing in the right source string.

Abhi Tk
  • 91
  • 7
1

Your logic in MaxWord is flawed: you always attempt to copy the last word encountered with the longest length. The type char is inappropriate for i and begin as these are offsets in text potentially larger than 127.

Furthermore, strncpy does not do what you think it does, it is an error prone function that can may not null terminate the destination buffer. Do not use this function.

Do not use gets either because it cannot be used safely, invalid input will cause a buffer overflow.

Here is a corrected version:

int MaxWord(const char *text, char *word) {
    int i, ctr = 0, max = 0, len, begin = 0, best = 0;

    len = strlen(text);
    for (i = 0; i < len; i++) {
        if (isalpha((unsigned char)text[i])) {
            if (ctr == 0) {
                begin = i;
            }
            ctr++;
        } else {
            if (ctr > max) {
                best = begin;
                max = ctr;
            }
            ctr = 0;
        }
    }
    memcpy(word, test + best, max);
    word[max] = '\0';
    printf("%s ", word);
    return max;
} 

It may seem surprising to cast text[i] as (unsigned char), but isalpha() is defined as taking an int argument with the value of an unsigned char or the constant EOF (usually defined as -1). If your compiler considers char to be a signed type, characters in text with the high bit set will be considered negative and will be sign extended when passed to isalpha potentially invoking incorrect or undefined behavior.

Another problem with your code is the determination of word boundaries: if you type in laengste correctly as längste, isalpha() may incorrectly consider the character or characters encoding the ä as a separator instead of a letter. Welcome to the intricate world of character encodings!

chqrlie
  • 131,814
  • 10
  • 121
  • 189
  • thank you it works ;,,,by the way the logic of MaxWord I learned from the school ,,, –  Dec 01 '15 at 21:15
  • @MahmoudAbosaleh: If this answer was useful, click on the up arrow to vote it up and on the gray check mark to accept it. Thank you. – chqrlie Dec 01 '15 at 21:50