getchar and character arrays

E

ehabaziz2001

Why I can not begin my subscript of character arrrays with 0.
In this program I can not do :

do
{
na=getchar();
i++;
na=getchar();

} while (na!='\n');


my program :
*-----------------------
void input(char *na)
{

int i=0;

printf ("Enter the name : ");
do
{
i++;

na=getchar();

} while (na!='\n');
}
 
P

pete

Why I can not begin my subscript of character arrrays with 0.
In this program I can not do :

do
{
na=getchar();
i++;
na=getchar();

} while (na!='\n');

my program :
*-----------------------
void input(char *na)
{

int i=0;


Your indexing would work OK, up to a point,
if you initialized this way:

int i = -1;
printf ("Enter the name : ");
do
{
i++;

na=getchar();

} while (na!='\n');
}


/* BEGIN pops_device.c */
/*
** If rc equals 0, then an empty line was entered
** and the array contains garbage values.
** If rc equals EOF, then the end of file was reached,
** or there is some input problem.
** If rc equals 1, then there is a string in array.
** Up to LENGTH number of characters are read
** from a line of a text stream.
** If the line is longer than LENGTH,
** then the extra characters are discarded.
*/
#include <stdio.h>

#define LENGTH 50
#define str(x) # x
#define xstr(x) str(x)

int main(void)
{
int rc;
char array[LENGTH + 1];

puts("The LENGTH macro is " xstr(LENGTH));
fputs("Enter a line with spaces:", stdout);
fflush(stdout);
rc = fscanf(stdin, "%" xstr(LENGTH) "[^\n]%*[^\n]", array);
if (!feof(stdin)) {
getc(stdin);
}
while (rc == 1) {
printf("Your string is:%s\n\n"
"Hit the Enter key to end,\nor enter "
"another line to continue:", array);
fflush(stdout);
rc = fscanf(stdin, "%" xstr(LENGTH) "[^\n]%*[^\n]", array);
if (!feof(stdin)) {
getc(stdin);
}
if (rc == 0) {
*array = '\0';
}
}
return 0;
}

/* END pops_device.c */
 
S

Simon Biber

pete said:
/* BEGIN pops_device.c */
/*
** If rc equals 0, then an empty line was entered
** and the array contains garbage values.
** If rc equals EOF, then the end of file was reached,
** or there is some input problem.
** If rc equals 1, then there is a string in array.
** Up to LENGTH number of characters are read
** from a line of a text stream.
** If the line is longer than LENGTH,
** then the extra characters are discarded.
*/
#include <stdio.h>

#define LENGTH 50
#define str(x) # x
#define xstr(x) str(x)

int main(void)
{
int rc;
char array[LENGTH + 1];

puts("The LENGTH macro is " xstr(LENGTH));
fputs("Enter a line with spaces:", stdout);
fflush(stdout);
rc = fscanf(stdin, "%" xstr(LENGTH) "[^\n]%*[^\n]", array);
if (!feof(stdin)) {
getc(stdin);
}
while (rc == 1) {
printf("Your string is:%s\n\n"
"Hit the Enter key to end,\nor enter "
"another line to continue:", array);
fflush(stdout);
rc = fscanf(stdin, "%" xstr(LENGTH) "[^\n]%*[^\n]", array);
if (!feof(stdin)) {
getc(stdin);
}

I suppose this getc is to grab the '\n' still stuck in stdin. Why not

rc = fscanf(stdin, "%" xstr(LENGTH) "[^\n]%*[^\n]%*c", array);

The %*c should match one character and not store it, right? Then you
don't need the if(!feof(stdin)) { getc(stdin); }
 
P

pete

Simon said:
Why not

rc = fscanf(stdin, "%" xstr(LENGTH) "[^\n]%*[^\n]%*c", array);

Thank you.
I don't know how to make that line work in a loop.
A subsequent call to fscanf, returns 0.

/* BEGIN pops_device.c */
/*
** If rc equals 0, then an empty line was entered
** and the array contains garbage values.
** If rc equals EOF, then the end of file was reached,
** or there is some input problem.
** If rc equals 1, then there is a string in array.
** Up to LENGTH number of characters are read
** from a line of a text stream.
** If the line is longer than LENGTH,
** then the extra characters are discarded.
*/
#include <stdio.h>

#define OLD_WAY 1

#define LENGTH 50
#define str(x) # x
#define xstr(x) str(x)

int main(void)
{
int rc;
char array[LENGTH + 1];

puts("OLD_WAY is " xstr(OLD_WAY));
puts("The LENGTH macro is " xstr(LENGTH));
fputs("Enter a line with spaces:", stdout);
fflush(stdout);

#if OLD_WAY != 0
rc = fscanf(stdin, "%" xstr(LENGTH) "[^\n]%*[^\n]", array);
if (!feof(stdin)) {
getc(stdin);
}
#else
rc = fscanf(stdin, "%" xstr(LENGTH) "[^\n]%*[^\n]%*c", array);
#endif


if (1 > rc) {
*array = '\0';
}
printf("rc is %d. Your string is:%s\n\n", rc, array);
while (rc == 1) {
fputs("Hit the Enter key to end,\nor enter "
"another line to continue:", stdout);
fflush(stdout);

#if OLD_WAY != 0
rc = fscanf(stdin, "%" xstr(LENGTH) "[^\n]%*[^\n]", array);
if (!feof(stdin)) {
getc(stdin);
}
#else
rc = fscanf(stdin, "%" xstr(LENGTH) "[^\n]%*[^\n]%*c", array);
#endif

if (1 > rc) {
*array = '\0';
}
printf("rc is %d. Your string is:%s\n\n", rc, array);
}
return 0;
}

/* END pops_device.c */
 
M

Mark McIntyre

Why I can not begin my subscript of character arrrays with 0.

you can. However your programme has two potential errors

1) in the first code fragment you do not initialise i, so it could
have any value

2) in the second code fragment, you increment i before you use it, so
you start off pointing to the 2nd element of the array.

I'm assuming you did declare na as an array.

--
Mark McIntyre

"Debugging is twice as hard as writing the code in the first place.
Therefore, if you write the code as cleverly as possible, you are,
by definition, not smart enough to debug it."
--Brian Kernighan
 
E

ehabaziz2001

So my my program should be like this after considering your points :
*----------------------------------------------------------------------------------------------
void input(char *na)
{

printf ("Enter the name : ");
do
{

na=getchar();
i++;


} while (na!='\n');
}
 
E

ehabaziz2001

So my my program should be like this after considering your points :
*----------------------------------------------------------------------------------------------
void input(char *na)
{

printf ("Enter the name : ");
do
{

na=getchar();
i++;


} while (na!='\n');
}
 
J

Jean Pierre Daviau

no
check for getchar() not return \n before assigning it to n

plus what the others said
 
E

ehabaziz2001

How can I do it with getchar() ?. I know to use it with scanf :
scanf ("\n%c");
 
J

Jean Pierre Daviau

How can I do it with getchar() ?. I know to use it with scanf :
scanf ("\n%c");
Transform this to a while with a bouble assignement, plus something of yours

do
{

na=getchar();
i++;


} while (na!='\n');
}
 
B

Ben Pfaff

That's not correct code. It needs a pointer to char argument.
Transform this to a while with a bouble assignement, plus something of yours

do
{

na=getchar();
i++;


} while (na!='\n');


This isn't correct code either. It sets the element after it sets.

Spurious }
 
S

Simon Biber

So my my program should be like this after considering your points :
*----------------------------------------------------------------------------------------------
void input(char *na)
{

printf ("Enter the name : ");
do
{

na=getchar();
i++;


} while (na!='\n');
}


No. That won't even compile -- you haven't defined i.

I have commented each of my additions to your code. Consider the
benefits of adding each one.

void input(char *na,
size_t n) /* extra param n tells this function how many
bytes are available in array na points to */
{
size_t i = 0; /* index variable starts at 0 */
int ch; /* ch holds character for the test */

if(n == 0) /* if no space available can only return */
return;
else if(n == 1) /* if only space for null terminator */
{
na[0] = 0;
return;
}

printf("Enter the name : ");

fflush(stdout); /* flushing because no newline was output */

do
{
ch = getchar();
na = ch;
i++;
} while(i < n - 1 /* leave space for null terminator */
&& ch != '\n' /* stop when enter is pressed or */
&& ch != EOF); /* there is an end-of-file or error */

na = 0; /* null-terminate the string */
}

It is important that ch is an int, not a char, because the EOF value is
distinct from the character values in the int returned from getchar. EOF
is a negative number, while the character values are non-negative.

When the result of getchar is assigned to a char, the EOF value (often
-1) and the character 255 often both map to -1. This would result in a
false detection of EOF when the character 255 was read from the stream.
 
C

CBFalconer

How can I do it with getchar() ?. I know to use it with scanf :
scanf ("\n%c");

What is 'it'? Read the following links.

--
If you want to post a followup via groups.google.com, ensure
you quote enough for the article to make sense. Google is only
a poor interface to usenet. There is no reason to assume your
readers can, or ever will, see any previous articles.
More details at: <http://cfaj.freeshell.org/google/>
Also see <http://www.safalra.com/special/googlegroupsreply/>
 
E

ehabaziz2001

Said before :
no
check for getchar() not return \n before assigning it to n

My question is :

How do I read \n with getchar() before going into the loop below do ..
while.

void input(char *na)
{
printf ("Enter the name : ");
do
{
na=getchar();
i++;
} while (na!='\n');
}
 
E

ehabaziz2001

Said before :
no
check for getchar() not return \n before assigning it to n
My question is :
/*-------------------------*/
I want my index to begin with 0 as any C Array as below . How do I read
\n with getchar() before going into the loop below do .. while.

void input(char *na)
{
printf ("Enter the name : ");
do
{
na=getchar();
i++;
} while (na!='\n');
}
 
E

ehabaziz2001

Said before :
no
check for getchar() not return \n before assigning it to n
My question is :
I want my index to begin with 0 as any C Array as below . How do I read

\n with getchar() before going into the loop below do .. while.
void input(char *na)
{
printf ("Enter the name : ");
do
{
na=getchar();
i++;
} while (na!='\n');
}
 
C

CBFalconer

Said before :
no
check for getchar() not return \n before assigning it to n
My question is :


Please don't top-post. Your answer belongs after (or intermixed
with) the snipped material you quote. Many people simply ignore
all top-posted articles. If you want help you should cooperate by
following normal usenet protocol. Read the following links:

--
Some informative links:
< <http://www.geocities.com/nnqweb/>
<http://www.catb.org/~esr/faqs/smart-questions.html>
<http://www.caliburn.nl/topposting.html>
<http://www.netmeister.org/news/learn2quote.html>
<http://cfaj.freeshell.org/google/>
 
E

ehabaziz2001

CBFalconer said:
Said before :
no
check for getchar() not return \n before assigning it to n
My question is :


Please don't top-post. Your answer belongs after (or intermixed
with) the snipped material you quote. Many people simply ignore
all top-posted articles. If you want help you should cooperate by
following normal usenet protocol. Read the following links:

--
Some informative links:
<<http://www.geocities.com/nnqweb/>
<http://www.catb.org/~esr/faqs/smart-questions.html>
<http://www.caliburn.nl/topposting.html>
<http://www.netmeister.org/news/learn2quote.html>
<http://cfaj.freeshell.org/google/>


oka i am sorry . Is it Oka ?

can I read '\n' using getchar() as I do in scanf ("\n") ?????

please suggested code :


void input (char *n)
////////////////////
{
int i=0;
printf ("\nInput :");
getchar()="\n";
do {
n=getchar();
i++;
} while (n!='\n');
}

void output (char *n)
////////////////////
{
int i=0;
printf ("\noutput :");
do {
printf ("%c" ,n);
i++;
} while (n!='\n');
}
 
C

CBFalconer

.... snip ...

can I read '\n' using getchar() as I do in scanf ("\n") ?????

please suggested code :

void input (char *n)
////////////////////
{
int i=0;
printf ("\nInput :");
getchar()="\n";
do {
n=getchar();
i++;
} while (n!='\n');
}

void output (char *n)
////////////////////
{
int i=0;
printf ("\noutput :");
do {
printf ("%c" ,n);
i++;
} while (n!='\n');
}


Don't use // comments in usenet messages, they can easily be
wrapped and destroy the code. Also try to post complete compilable
programs, with proper indentation. Don't use tabs, because they
are often lost entirely.

'\n' is just another character. If you know that the input
contains an unread one you can flush it with a routine such as the
following:

int flushln(FILE *f) {
int ch;

while ((EOF != (ch = getc(f)) && ('\n' != ch)) continue;
return ch;
}

Calling this guarantees that any '\n' in the input has been
absorbed. It doesn't ensure that there was such to be absorbed.
Note that the input is stored in an int, so that EOF can be
detected. Also note that all input lines (on a buffered system,
which yours almost certainly is) terminate in a '\n'.

Now let us assume that you want to input lines not exceeding some
sort of maximum length, and are willing to discard any input longer
than that maximum. First you must define the maximum length
somewhere:

#define MAXLGH 80 /* just to pick a number out of the hat */

and somewhere you will have a buffer to hold the lines:

char buffer[MAXLGH];

now you want to call a routine to fill that buffer, and discard any
excess length:

void fillbuf(char *buf, int maxlgh); /* A prototype */

(which I haven't used - I combined it with something that prompts)

Putting things together you might end up with a program that looks
like:

#include <stdio.h>
#define MAXLGH 10

/* -------------- */

int flushln(FILE *f) {
int ch;

while ((EOF != (ch = getc(f))) && ('\n' != ch)) continue;
return ch;
}

/* -------------- */

int getinput(FILE *f, char *buf, int lgh, char *prompt) {
int i;
int ch;

fputs(prompt, stdout);
fflush(stdout);
i = 0;
while ((i < lgh) && (EOF != (ch = getc(f))) && ('\n' != ch)) {
/* study the above condition carefully,
especially the order of tests.
Note that with lgh > 0 getc is always called */
buf[i++] = ch;
}
/* Now decide why the loop ended. */
if ('\n' != ch) ch = flushln(f);
/* This assumes that EOF is sticky. Don't worry about it */

/* Now we know that any final '\n' has been absorbed */

/* important - terminate the string */
buf = '\0';
return ch;
}

/* -------------- */

int main(void) {

char buffer[MAXLGH + 1]; /* +1 allows for terminating '/0' */
char prompt[] = "Input: ";

while (EOF != getinput(stdin, buffer, MAXLGH, prompt)) {
fputs("Output: ", stdout); /* no appended '\n' */
puts(buffer); /* which appends a '\n' and forces output */
}
return 0; /* main always returns a value */
}

Note that the program terminates on receiving an EOF signal. How
this is done depends on your system. Under linux that will
probably be a CTL-d key. Under MSDOS or Windows that will probably
be a CTL-z key. Entered immediately after the "Input:" prompt.

Lines terminate on receiving a '\n', generated by the Enter key.
Storage terminates either on line termination or receiving MAXLGH
characters.

Aside: It would be well to add a 'static' in the headers of the
functions (other than main), but this won't affect anything until
you get into more complicated multi-file programs.

getchar() is just shorthand for getc(stdin). Routines are more
flexible when you can aim them at arbitrary files. Keep them as
simple as possible.

Don't use scanf for interactive input. It will always leave
confusion. When and if you do use it always check its return
value.

Carefully read the descriptions of each standard function I have
called. This includes getc, getchar, puts, fputs, fflush. Note
that they all do simple things.
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

No members online now.

Forum statistics

Threads
473,769
Messages
2,569,579
Members
45,053
Latest member
BrodieSola

Latest Threads

Top