How to count characters in a string after splitting the word? - c

I found this c programming code on https://www.includehelp.com/c-programs/c-program-to-split-string-by-space-into-words.aspx
/*C program to split string by space into words.*/
#include <stdio.h>
#include <string.h>
int main()
{
char str[100];
char splitStrings[10][10]; //can store 10 words of 10 characters
int i,j,cnt;
printf("Enter a string: ");
gets(str);
j=0; cnt=0;
for(i=0;i<=(strlen(str));i++)
{
// if space or NULL found, assign NULL into splitStrings[cnt]
if(str[i]==' '||str[i]=='\0')
{
splitStrings[cnt][j]='\0';
cnt++; //for next word
j=0; //for next word, init index to 0
}
else
{
splitStrings[cnt][j]=str[i];
j++;
}
}
printf("\nOriginal String is: %s",str);
printf("\nStrings (words) after split by space:\n");
for(i=0;i < cnt;i++)
printf("%s\n",splitStrings[i]);
return 0;
}
I had run this code and I have entered the string for an example "The dog is sad" The output will be
The
Dog
Is
Sad
I was wondering if I could count the numbers of the characters after splitting the word; like for an example;
The 3
Dog 3
Is 3
Sad 3
I do not know how to achieve that desired output. Thank you

Your last printf could be:
printf("%s %d ",splitStrings[i], strlen(splitStrings[i]));
You already use strlen() in your first for loop.

Use this modified printf:
/*C program to split string by space into words.*/
#include <stdio.h>
#include <string.h>
int main()
{
char str[100];
char splitStrings[10][10]; //can store 10 words of 10 characters
int i,j,cnt;
printf("Enter a string: ");
gets(str);
j=0; cnt=0;
for(i=0;i<=(strlen(str));i++)
{
// if space or NULL found, assign NULL into splitStrings[cnt]
if(str[i]==' '||str[i]=='\0')
{
splitStrings[cnt][j]='\0';
cnt++; //for next word
j=0; //for next word, init index to 0
}
else
{
splitStrings[cnt][j]=str[i];
j++;
}
}
printf("\nOriginal String is: %s",str);
printf("\nStrings (words) after split by space:\n");
for(i=0;i < cnt;i++)
printf("%s %d ",splitStrings[i],strlen(splitStrings[i]));//modified
return 0;
}

Related

why does the statements inside loop condition execute when condition is false in c programming?

I am just running a code to find the length of a given string input by the user in C programming language. I used a loop condition to determine the length but statements inside loop executes when the condition is false also. The code I have tried in c is:
#include <stdio.h>
#define ArrayLength 50
int StringLengthCount();
int main() {
printf("Hello, World!\n");
/*Question: Find inserted string's length, without build in function*/
int c=StringLengthCount();
printf("Your inserted string's length is:%d",c);
return 0;
}
int StringLengthCount(){
printf("\n");
printf("Please enter a sentence to find its length of character:");
char array1[ArrayLength];
fgets(array1,ArrayLength,stdin);
printf("Your inserted string is:%s\n",array1);
int i=0;
int count=0;
while(array1[i]!='\0'){
count++;
printf("%d character is %c",count,array1[i]);
printf("\n");
i++;
}
printf("\n");
printf("Your inserted string's total character i.e string length is:%d",count);
}
I am expecting the result 2 for a sample string input "we", but it gives result 3.
The output result in CLion compiler is given below
enter image description here
Can you kindly tell me why it happens?
If by "statements inside loop executes when the condition is false also" you mean that you see an extra character every time you execute remember that also the line feed (LF alias \n) character that you use to enter your string is part of the acquired string.
So even the empty string has one character that is \n or 0x10.
Your check should be something like this:
while (array1[len] != '\0' && array1[len] != '\n' )
And you function, as suggested in the comments, should have a return and could use just one variable like this:
int StringLengthCount() {
printf("\n");
printf("Please enter a sentence to find its length of character:");
char array1[ArrayLength];
fgets(array1, ArrayLength, stdin);
printf("Your inserted string is:%s\n", array1);
int len = 0;
while (array1[len] != '\0' && array1[len] != '\n' ) {
printf("%d character is %c", len + 1, array1[len]);
printf("\n");
len++;
}
printf("\n");
printf("Your inserted string's total character i.e string length is:%d\n\n",
len);
return len;
}
The function fgets will also read the newline character, so you need to change the condition in the while-loop from str[i] != '\0' to str[i] != '\n'. I have also implemented the suggested changes by Devolus.
#include <stdio.h>
#include <stdlib.h>
#define LEN 50
void string_length();
int main(void)
{
string_length();
return EXIT_SUCCESS;
}
void string_length(void)
{
printf("Enter a string: ");
char str[LEN];
fgets(str, LEN - 1, stdin);
printf("Your entered string is: %s\n", str);
int i = 0;
while (str[i] != '\n') {
printf("The %d. character is '%c'.\n", i + 1, str[i]);
++i;
}
printf("\nThe string's length is %d.\n", i);
}

Alphabetize words in sentence in C?

I am trying to take words in a sentence and alphabetize them each. it has to be able to differentiate between upper and lower case letters but i am having trouble getting it to do just lower case letters.
If I input one word at a time it will alphabetize it but once I input multiple words it acts weird. If I input "i need help", I expect to receive "i deen ehlp"; instead I receive "i dnee ehlp"
Here is my code:
#include <stdio.h>
#include <string.h>
int main (void)
{
int i, j, k, l=0, m=0, s=0, N=100;
printf("input a sentence with no more than 100 characters \n");
char sentence[N];
scanf("%[^\n]s", sentence);
int slength=strlen(sentence);
printf("Sentence before sorting - %s \n", sentence);
/*capital string keeps track of position of capital letters*/
int capital[slength];
for (i = 0; i < slength-1; i++)
{
for (j = i+1; j < slength; j++)
{
/*make uppercase letters lowercase */
if (sentence[j-1] <=90 && sentence[j-1]>64)
{
capital[l]=i;
sentence[i]=sentence[i]+32;
}
/* skip to next word if a space is detected */
if(sentence[j]==' ')
{
i=j+1;
j=j+2;
}
/*alphabetize loop*/
if (sentence[i] > sentence[j])
{
k = sentence[i];
sentence[i] = sentence[j];
sentence[j] = k;
}
}
}
printf("Sentence after sorting - %s \n", sentence);
return 0;
}
This is a very simple solution.
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include <ctype.h>
int letter_sort(const void* a, const void* b)
{
return tolower(*(const char*)a) - tolower(*(const char*)b);
}
char* sentence_sort(char* s)
{
char _[strlen(s)+1];
strcpy(_,s);
for(char* w = strtok(_, " ."); w; w = strtok(NULL, " ."))
{
qsort(w, strlen(w), !!w, letter_sort);
memcpy(s+(w-_), w, strlen(w));
}
return(s);
}
int main(void) {
char sent[101];
printf("Input a sentence with no more than 100 characters \n");
scanf("%[^\n]", sent);
printf("Sentence before sorting: %s\n", sent);
printf("Sentence after sorting: %s\n", sentence_sort(sent));
return 0;
}
Output
Success #stdin #stdout 0s 9424KB
Input a sentence with no more than 100 characters
Sentence before sorting: The quick Brown fox Jumped over the Lazy Dogs.
Sentence after sorting: ehT cikqu Bnorw fox deJmpu eorv eht aLyz Dgos.

Exiting Do While loop

I was working on some homework, and came across this issue.
Write a program that reads several lines of text and prints a table indicating the number of one-letter words, two-letter words,
three-letter words, and so on, appearing in the text. For example the
phrase "Whether 'tis nobler in the mind to suffer"
Will contain
1 letter words: 0
2 letter words: 2
3 letter words: 1
4 letter words: 2 (including 'tis)
5 letter words: 0
6 letter words: 2
7 letter words: 1
My code for the question is below.
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#define MAXDIMENSIONS 1000 //set max dimensions
#define MAXLENGTH 1000 //set max length
void separate(char stringArray[][MAXLENGTH], int words);
void printTable(char stringArray[][MAXLENGTH], int c);
int main(int argc, char** argv) {
char txt[MAXLENGTH];
char *token;
char mat[MAXDIMENSIONS][MAXLENGTH];
int i=0,wordcount=0;
do{
printf(">>>Write and press enter (EXIT for end of program)<<< : ",49);
fgets(txt,sizeof txt,stdin);
if(strcmp(txt,"EXIT")!=0)
{
token=strtok(txt," ");
strcpy(mat[i],token);
i++;
while(token!=NULL){
token=strtok(NULL, " ");
if(token!=NULL){
strcpy(mat[i],token);
i++;
}
}
}
}while(strcmp(txt,"EXIT")!=0);
separate(mat,i);
printTable(mat,i);
return (EXIT_SUCCESS);
} // end of main
void separate(char stringArray[][MAXLENGTH], int words){
for(int i=0; i<words; i++){
for(int j=0; j<strlen(stringArray[i]); j++){
if((stringArray[i][j]<65 && stringArray[i][j]!=39) || (stringArray[i][j]>90 && stringArray[i][j]<97)|| stringArray[i][j]>122){
for(int g=j; g<strlen(stringArray[i]); g++){
stringArray[i][g]=stringArray[i][g+1];
}
}
}
}
}
void printTable(char stringArray[][MAXLENGTH], int c){
int max;
int value=0,j;
max=strlen(stringArray[0]);
for(int i=1; i<c; i++){
if(max<strlen(stringArray[i])){
max=strlen(stringArray[i]);
}
}
printf("\n***********WORD LENGTH READER***********\n");
printf("| LENGTHS || VALUES | \n");
for(j=1; j<=max; j++){
for(int i=0; i<c; i++){
if(strlen(stringArray[i])==j){
value++;
}
}
printf("| %d || %d | \n",j,value);
value=0;
}
printf("\n****************************************\n");
}
My issue is getting out of the do while loop on line 17-33. It is my first time using fgets and I believe that this is probably what is causing the issue. I had written the code using gets and it works like that, but I know that gets is not supposed to be used due to its vulnerability.
Any help is appreciated.
Thanks in advance!
Because fgets also reads the newline, your exit condition will not be met because of the newline. You can either include the newline in your check, "EXIT\n" or you can patch out the newline after fgets.
The following example also makes the loop a bit simpler:
do {
fgets(txt,sizeof txt,stdin);
char *p= strrchr(txt,'\n'); if (p) *p= '\0';
if(strcmp(txt,"EXIT")==0)
break;
//....
while(1);

C storing strings into an array

I'm working in a problem from the "C programming a Modern Approach 2nd Edition" text. I want to write a program that writes the smallest and largest words. The program stops accepting inputs when the user enters a 4-letter word.
I'm using an array of strings to solve this but I can't even get my program to store words in it.
#include <stdio.h>
#include <string.h>
#define WORD_LEN 20
int main()
{
char word[WORD_LEN]={0},ch;
char *a[10]={}; //Max 10 words in the array
int i=0,j;
for(;;)
{
printf("Enter a word: ");
fgets(word,WORD_LEN,stdin);
strtok(word, "\n"); //removes newline
a[i] = word;
if(strlen(word) == 4) //if word is 4 characters
break; //break out of loop
i++;
}
for(j=0;j<i;j++) //displaying array
printf("%s\n",a[j]);
return 0;
}
Output:
Enter a word: Analysis
Enter a word: Martin
Enter a word: Jonathan
Enter a word: Dana
Dana
Dana
Dana
Any idea into what I'm doing wrong? Thanks.
As BLUEPIXY mentioned, you are storing same address in all a[i]s. So at the end of the loop, it prints the last output i times.
Solution:
You need to allocate memory for a[i] and copy the strings.
#include <stdio.h>
#include <string.h>
#define WORD_LEN 20
#define MAX_NUM_WORD 10 //Max 10 words in the array
int main()
{
char word[WORD_LEN]={0},ch;
char *a[MAX_NUM_WORD]={0};
int i=0,j;
for(;;)
{
printf("Enter a word: ");
fgets(word,WORD_LEN,stdin);
strtok(word, "\n"); //removes newline
a[i] = malloc(sizeof(char)* (strlen(word)+1)); //1 for '\0'
strcpy(a[i], word);
i++;
if(strlen(word) == 4) //if word is 4 characters
break; //break out of loop
//i++; //You will be missing last 4 letter word if i++ is here.
if(MAX_NUM_WORD <= i) //You can store only MAX_NUM_WORD strings
break;
}
for(j=0;j<i;j++) //displaying array
printf("%s\n",a[j]);
//Your other code.
for(i=0; i<MAX_NUM_WORD && NULL != a[i]; i++)
free(a[i]); //Free the allocated memory.
return 0;
}
Adding to others answers, when using malloc to allocate memory for your strings, it is good to also check the return value of void* pointer returned from it.
Additionally, it is also safe to check the return value of fgets, just to be super safe.
This solution demonstrates these points:
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#define WORD_LEN 20
#define MAX_NUM_WORD 10
#define EXIT_LEN 4
int
main(void) {
char word[WORD_LEN];
char *a[MAX_NUM_WORD];
int i = 0, wrd;
while (i < MAX_NUM_WORD) {
printf("Enter a word: ");
if (fgets(word, WORD_LEN, stdin) != NULL) {
word[strlen(word)-1] = '\0';
}
a[i] = malloc(strlen(word)+1);
if (a[i] == NULL) {
fprintf(stderr, "%s\n", "Malloc Problem");
exit(EXIT_FAILURE);
}
strcpy(a[i], word);
i++;
if (strlen(word) == EXIT_LEN) {
break;
}
}
// Print and free, all at once.
for (wrd = 0; wrd < i; wrd++) {
printf("%s\n", a[wrd]);
free(a[wrd]);
a[wrd] = NULL;
}
return 0;
}

Split a string between words and insert newlines

i have a string that is made out of a few sentences.
for example:
hello world bye bye
now, i need to make this sentence into a coulmn of words:
hello
world
bye
bye
i have this idea going on, but i dont know how to write it correctly, so i was hopiny ypu guys could help me out.
this is what i have so far:
int len=0, k=0, stopatspace=0;
char temptext[100][15]={0};
char line[300]={0};
len=strlen(line);
printf("len is: %d", len);
for(k=0; k<len; k++)
{
if (k == ' ')
{
// i dont know what to write here in order to make it a cloumn
}
}
basiclly, my idea is to run on all the length of my line and when i reach a space i want it to enter (to go one line down so that it will look like a coulmn)
Suppose line is the char array that contains hello world bye bye and text is declared as
char text[100][15]; //I used 100 and 15 because your example contains it
and you want each word to be copied into each row of text. Then,use strtok() function with " "(space) as delimeter and place this in a loop that terminates when strtok() returns NULL to get each word. Copy each word to each row of text using strcpy() in the loop.
The code for this will look like this:
char text[100][15];
char line[]="hello world bye bye";
int i=0;
char *token=strtok(line," ");
while(token!=NULL)
{
strcpy(text[i],token);
i++;
token=strtok(NULL," ");
}
Now, to print it,you can use
for(int j=0;j<i;j++)
printf("text[%d]=%s",j,text[j]);
Another method would be to manually copy each character until a space is seen.
int len=strlen(line);
int i=0;
int k=0;
for(int j=0;j<len+1;j++)
{
if(line[j]==' ')
{
text[i][k]='\0';
i++;
k=0;
}
else
{
text[i][k]=line[j];
k++;
}
}
Note that the above code does not prevent buffer overflows. You can print each word using
for(int j=0;j<i+1;j++)
printf("text[%d]=%s",j,text[j]);
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
int main(int argc, char *argv[])
{
char string[100];
fgets(string, 100, stdin);
string[strlen(string)-1] = 0;
// create an array of pointers
char **string_array = (char**)malloc(sizeof(char*));
int i = 0, array_size;
// tokenize input
char *token = strtok(string, " ");
while(token!=NULL) {
// dynamically increase the array during run time
string_array = (char**)realloc(string_array, (i+1)*sizeof(char**));
// create the string as you would do when there is only one string
string_array[i] = (char*)malloc(strlen(token)+1);
strcpy(string_array[i], token);
token = strtok(NULL, " ");
i++;
}
array_size = i;
for(i=0; i<array_size; i++) {
printf("%s\n", string_array[i]);
}
return 0;
}
Basically you create an array of pointers and you allot memory for the strings one by one as you would do when there is only one string.
(if number of token is unknown, use realloc to increase the size of pointer to pointers.)
#include <stdio.h>
#include <ctype.h>
int main(void){
char line[300] = "hello world bye bye\n";
char temptext[100][15]={0};
int i=0, j, k=0;
while(line[k]){
if(isspace(line[k])){
++k;//skip space to word
continue;
}
for(j=0; j < 15-1 && line[k] && !isspace(line[k]); ++k, ++j)
temptext[i][j] = line[k];
if(j && ++i == 100)
break;
}
for(j=0; j<i; ++j)
puts(temptext[j]);
return 0;
}
#include<stdio.h>
#define NEWLINE printf("\n")
int main(void)
{
char string[]="hello world bye bye";
int index=0;
while(string[index])
{
if(string[index]==32)
{
NEWLINE;
index++;
}
else
{
printf("%c",string[index]);
index++;
}
}
NEWLINE;
}
// Whenever i encountered with a space, i am printing a new line on the screen. Here 32 is the ASCII value for space

Resources