Does the fgets() function always force the NULL character inside char? - input

Rather simple question about the fgets()-function.
As I understood, the fgets() function wants to add newline: \n and NULL: \0 at the end.
So. If i give input: car
Then: char line[5] = {c,a,r,\n,\0} , isn't that so?
But, the question is: what if I give carB as input?
Is it then: char line[5] = {c,a,r,b,\0} ?
So, does fgets() always force the NULL character inside the char line?
int main(void){
char line[5];
printf("Give an input. Please give max length of 3 characters so fgets can put newline and NULL inside ");
fgets(line, 5, stdin);
return 0;
}

Related

Can't put a space between output and input on the same line

After printing, if I write the name I get:
Insert a name :Andrea
There is no space before Andrea, even if I put the space in the output. How can I add a space before writing the name?
#include <stdio.h>
int main() {
int string[8];
printf("\nInsert a name : ");
printf(" ");
scanf("%s", string);
printf("\nThe name is : %s", string);
return 0;
}
The code that you provided does not compile because the variable string is an array of integers (and not a string as you might think). And when you input the value of it, you're telling the compiler to expect a string ("%s" in scanf("%s", string")).
Change your string declaration to char string[8] and it should work (with the spacing you want):
Note that the value that goes into string will not contain more than 8 characters.
Actually, you did a small mistake in your code, you declared the string to be an array of int & from the code scanf("%s", string") the compiler expects from the user to enter a string as it contains %s as the format specifier. Hence, the code doesn't compile.
In order to correct this, you should declare string as char string[8] (string containing 8 characters).
The correct code is given below :
#include <stdio.h>
int main() {
char string[8];
printf("\nInsert a name : ");
scanf("%s", string);
printf("\nThe name is : %s", string);
return 0;
}
From the above correction your problem for space between input and output will be solved!
Here, is the output which is received from this correction :
I hope so this explanation will be helpful for you!
If any problem persists then feel free to ask in comments! ;-)

sprintf doesn't seem to grab zeroth string

I have the following code:
#include <stdio.h>
int main(void) {
char list[3][7] = { "One", "Two", "Three"} ;
char item[7]; // originally I had posted "char item[3];" by mistake
int i;
for( i=0; i<2; i++ ) {
sprintf(item, "%-7s", list[i]);
printf( "%d %s", i, item );
}
printf("\n\r");
for( i=0; i<2; i++ ) {
sprintf(item, "%-7s", list[i]);
printf( "%d %s", i, item );
}
printf("\n\r");
return 0;
}
I expect the following output
0 One 1 Two
0 One 1 Two
However, instead I get:
0 One 1 Two
0 1 Two
Note the missing text "One" the second time it prints.
Can someone explain what's happening here?
Thanks!
With item declared as:
char item[7];
the code exposes undefined behaviour because sprintf(item, "%-7s") attempts to write at least 8 characters into item.
The documentation of sprintf() explains (the emphasis is mine):
Writes the results to a character string buffer. The behavior is undefined if the string to be written (plus the terminating null character) exceeds the size of the array pointed to by buffer.
-7 in the format string "%-7s" is interpreted as:
(optional) integer value or * that specifies minimum field width. The result is padded with space characters (by default), if required, on the left when right-justified, or on the right if left-justified. In the case when * is used, the width is specified by an additional argument of type int. If the value of the argument is negative, it results with the - flag specified and positive field width. (Note: This is the minimum width: The value is never truncated.)
In order to avoid the undefined behaviour, the size of item must be at least 8 but keep in mind that if the string to format is longer than 7 characters it is not truncated, the result becomes longer than 8 characters and it overflows item again.
Why you get the output you get?
The calls to sprintf(item, "%-7s", list[i]); in the first loop write 8 characters in a buffer of 7 characters. The extra character (which is \0) incidentally happens to overwrite the first character of list[0] changing it into an empty string. This is just one random behaviour, compiling the code with a different compiler or different compiling options could produce a different behaviour.
When you do the sprintf(item, "%-7s", list[i]); you are, essentially, copying the string from list[i] into your char array item.
So list[2] -> "three" is 5 chars plus the nul terminator, but item is only 3 chars long -- you are overflowing item and writing over some other memory, which could very well be part of list.
Change item to be char item[7] so it matches the length of 7 declared in your 2nd dimension in list[3][7]. When I did that I got your expected output.
(I used https://repl.it/languages/C to test)

xbuf_repl is not replacing all occurences

As g-wan documented, xbuf_repl is replacing all occurrences. But my installed g-wan, running the following code, only replaced the first occurrence of the matched.
#include "gwan.h"
int main(int argc, char* argv[]){
xbuf_t *reply = get_reply(argv);
char str[ ] = "kjfdkkkkfldjfjfldkjdkkklfjworhg8kkkugpugulrghkkkr8g";
xbuf_ncat(reply, str, sizeof(str)-1);
xbuf_repl(reply, "kkk", "((()))");
return 200;
}
output is : kjfd((()))kfldjfjfldkjdkkklfjworhg8kkkugpugulrghkkkr8g
What's wrong of my code? How to work around it?
In the entity.c G-WAN example, you can see:
// escape '<' because it cuts the text
while(xbuf_replfrto(reply, pos, reply->ptr + reply->len - 13, "<", "<"));
This while() makes it obvious that one instance is replaced at a time, which is confirmed by the G-WAN documentation:
// replace the first occurence of the 'old' string by the 'new' string in the buffer
char *xbuf_repl (xbuf_t *ctx, char *old, char *new);
According to the G-WAN API documentation . . .
// replace the first occurence of the 'old' string by the 'new' string in the buffer
char *xbuf_repl (xbuf_t *ctx, char *old, char *new);
G-WAN also has this API, which (as I just learned from Gil's answer) also only replaces the first occurrence but within a range of the buffer rather than first occurrence from the beginning of the buffer . . . .
// same as above but using a range in the buffer
char *xbuf_replfrto(xbuf_t *ctx, char *beg, char *end, char *old, char *new);
Gil's answer shows how you can make use of this to replace ALL occurrences within the buffer.
Ken

printf(), fprintf(), wprintf() and NSlog() won't print on XCode

I'm doing a small app for evaluating and analyzing transfer functions. As boring as the subject might seem to some, I want it to at least look extra cool and pro and awesome etc... So:
Step 1: Gimme teh coefficients! [A bunch of numbers]
Step 2: I'll write the polynomial with its superscripts. [The bunch of numbers in a string]
So, I write a little C parser to just print the polynomial with a decent format, for that I require a wchar_t string that I concatenate on the fly. After the string is complete I quickly try printing it on the console to check everything is ok and keep going. Easy right? Welp, I ain't that lucky...
wchar_t *polynomial_description( double *polyArray, char size, char var ){
wchar_t *descriptionString, temp[100];
int len, counter = 0;
SUPERSCRIPT superscript;
descriptionString = (wchar_t *) malloc(sizeof(wchar_t) * 2);
descriptionString[0] = '\0';
while( counter < size ){
superscript = polynomial_utilities_superscript( size - counter );
len = swprintf(temp, 100, L"%2.2f%c%c +", polyArray[counter], var, superscript);
printf("temp size: %d\n", len);
descriptionString = (wchar_t *) realloc(descriptionString, sizeof(wchar_t) * (wcslen(descriptionString) + len + 1) );
wcscat(descriptionString, temp);
counter++;
}
//fflush(stdout); //Already tried this
len = wprintf(L"%ls\n", descriptionString);
len = printf("%ls**\n", descriptionString);
len = fprintf(stdout, "%ls*\n", descriptionString);
len = printf("FFS!! Print something!");
return descriptionString;
}
During the run we can see temp size: 8 printed the expected number of times ONLY WHILE DEBUGGING, if I run the program I get an arbitrary number of prints each run. But after that, as the title states, wprintf, printf and fprintf don't print anything, yet len does change its size after each call.
In the caller function, (application:(UIApplication *)application didFinishLaunchingWithOptions:, while testing) I put an NSLog to print the return string, and I dont get ANYTHING not even the Log part.
What's happening? I'm at a complete loss.
Im on XCode 4.2 by the way.
What's the return value from printf/wprintf in the case where you think it's not printing anything? It should be returning either -1 in the case of a failure or 1 or more, since if successful, it should always print at least the newline character after the description string.
If it's returning 1 or more, is the newline getting printed? Have you tried piping the output of your program to a hex dumper such as hexdump -C or xxd(1)?
If it's returning -1, what is the value of errno?
If it turns out that printf is failing with the error EILSEQ, then what's quite likely happening is that your string contains some non-ASCII characters in it, since those cause wcstombs(3) to fail in the default C locale. In that case, the solution is to use setlocale(3) to switch into a UTF-8 locale when your program starts up:
int main(int argc, char **argv)
{
// Run "locale -a" in the Terminal to get a list of all valid locales
setlocale(LC_ALL, "en_US.UTF-8");
...
}

loop on prompt with a yes or no?

Good afternoon,
I'm trying to accomplish a task that i know should be doable. however my attempts seem to fail every time. My endeavor is to learn to code in Objective -c and have been making good progress. what i would like to do is add a loop to my current application that asks at the end if i would like to run again or some thing to that regard, and reply with a yes or no. if no the program ends and if yes it jumps back to the top of the project to start all over. kinda like what i have below? forgive me please if its not quite perfect, im still getting used to programing and am finding it incredibly fun.
#include <stdio.h>
int main(void)
{
char loop = yes;
while (loop = yes)
{
.
.
.
}
printf ("would you like to continue (yes/no)/n");
scanf ("%s", loop);
}
The printf and scanf need to be moved up inside the curly braces of the while loop. Also, you want \n instead of /n in the printf. Finally, you're going to get a string back with that scanf() call, so you'll want to declare loop as a char array, and then in the while loop, check the first element of that array for a 'y' or 'n' or something like that. You might also want to look at getchar() instead of scanf() for that sort of thing.
Not compiled here, but should work:
#include <stdio.h>
int main(void)
{
char buffer[256];
do {
.
.
.
printf ("would you like to continue (yes/no)/n");
scanf ("%s", buffer);
} while (strcmp(buffer,"yes") != 0);
}
One wouldn't do anything like that in a real world application, but for demonstration purpose it should be ok.
I made your variable an array, because strings are arrays of characters in C. Length is set to 256 bytes (255 characters + 0-byte as delimiter). I changed the loop to do-while to make it run at least once. For string comparison you need to call a function. strcmp returns 0 for identical strings. Finally, the question belongs in the loop.
It is plain C though, using nothing of Objective-C.
int main() {
char A = 'n';
char B = 'y';
char Answer;
printf("Does the subject have a glazed over look? (y/n): \n");
scanf("%c",&Answer);
if (Answer=='N'||Answer=='y'|| Answer=='N'||Answer=='Y')
printf("Good\n");
else
printf("Please enter 'y' or 'n' \n ");
return 0;
}
#include <stdio.h>
int main(void)
{
avi;
char loop[10];
while (loop = yes)
{
.
.
.
}
printf ("would you like to continue (yes/no)/n");
scanf ("%s", loop);
if(strcpm(loop,"YES")==0) goto avi:
}