Split a string based on contiguous delimiters - c

I'm looking to split a sting based on a specific sequence of characters but only if they are in order.
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
int main()
{
int i = 0;
char **split;
char *tmp;
split = malloc(20 * sizeof(char *));
tmp = malloc(20 * 12 * sizeof(char));
for(i=0;i<20;i++)
{
split[i] = &tmp[12*i];
}
char *line;
line = malloc(50 * sizeof(char));
strcpy(line, "Test - Number -> <10.0>");
printf("%s\n", line);
i = 0;
while( (split[i] = strsep(&line, " ->")) != NULL)
{
printf("%s\n", split[i]);
i++;
}
}
This will print out:
Test
Number
<10.0
However I just want to split around the -> so it could give the output:
Test - Number
<10.0>

I think the best way to do the splits with an ordered sequence of delimeters is
to replicate strtok_r behaviour using strstr, like this:
#include <stdio.h>
#include <string.h>
char *substrtok_r(char *str, const char *substrdelim, char **saveptr)
{
char *haystack;
if(str)
haystack = str;
else
haystack = *saveptr;
char *found = strstr(haystack, substrdelim);
if(found == NULL)
{
*saveptr = haystack + strlen(haystack);
return *haystack ? haystack : NULL;
}
*found = 0;
*saveptr = found + strlen(substrdelim);
return haystack;
}
int main(void)
{
char line[] = "a -> b -> c -> d; Test - Number -> <10.0> ->No->split->here";
char *input = line;
char *token;
char *save;
while(token = substrtok_r(input, " ->", &save))
{
input = NULL;
printf("token: '%s'\n", token);
}
return 0;
}
This behaves like strtok_r but only splits when the substring is found. The
output of this is:
$ ./a
token: 'a'
token: ' b'
token: ' c'
token: ' d; Test - Number'
token: ' <10.0>'
token: 'No->split->here'
And like strtok and strtok_r, it requires that the source string is
modifiable, as it writes the '\0'-terminating byte for creating and returning
the tokens.
EDIT
Hi, would you mind explaining why '*found = 0' means the return value is only the string in-between delimiters. I don't really understand what is going on here or why it works. Thanks
The first thing you've got to understand is how strings work in C. A string is
just a sequence of bytes (characters) that ends with the '\0'-terminating
byte. I wrote bytes and characters in parenthesis, because a character in C is
just a 1-byte value (on most systems a byte is 8 bit long) and the integer
values representing the characters are those defined in the ASSCI code
table, which are 7-bit long values. As you can see from the table the
value 97 represents the character 'a', 98 represents 'b', etc. Writing
char x = 'a';
is the same as doing
char x = 97;
The value 0 is an special value for strings, it is called NUL (null character)
or '\0'-terminating byte. This value is used to tell the functions where a
string ends. A function like strlen that returns the length of a string, does
it by counting how many bytes it encounters until it encounters a byte with
the value 0.
That's why strings are stored using char arrays, because a pointer to an array
gives to the start of the memory block where the sequence of chars is stored.
Let's look at this:
char string[] = { 'H', 'e', 'l', 'l', 'o', 0, 48, 49, 50, 0 };
The memory layout for this array would be
0 1 2 3 4 5 6 7 8 9
+-----+-----+-----+-----+-----+----+-----+-----+-----+----+
| 'H' | 'e' | 'l' | 'l' | 'o' | \0 | '0' | '1' | '2' | \0 |
+-----+-----+-----+-----+-----+----+-----+-----+-----+----+
or to be more precise with the integer values
0 1 2 3 4 5 6 7 8 9 10
+----+-----+-----+-----+-----+---+----+----+----+---+
| 72 | 101 | 108 | 108 | 111 | 0 | 48 | 49 | 50 | 0 |
+----+-----+-----+-----+-----+---+----+----+----+---+
Note that the value 0 represents '\0', 48 represents '0', 49 represents
'1' and 50 represents '2'. If you do
printf("%lu\n", strlen(string));
the output will be 5. strlen will find the value 0 at the 5th position and
stop counting, however string stores two strings, because from the 6th
position on, a new sequence of characters starts that also terminates with 0, thus making it a
second valid string in the array. To access it, you would need to have pointer
that points past the first 0 value.
printf("1. %s\n", string);
printf("2. %s\n", string + strlen(string) + 1);
The output would be
Hello
012
This property is used in functions like strtok (and mine above) to return you
a substring from a larger string, without the need of creating a copy (that would be
creating a new array, dynamically allocating memory, using strcpy to create
the copy).
Assume you have this string:
char line[] = "This is a sentence;This is another one";
Here you have one string only, because the '\0'-terminating byte comes after
the last 'e' in the string. If I however do:
line[18] = 0; // same as line[18] = '\0';
then I created two strings in the same array:
"This is a sentence\0This is another one"
because I replaced the semicolon ';' with '\0', thus creating a new string
from position 0 to 18 and a second one from position 19 to 38. If I do now
printf("string: %s\n", line);
the output will be
string: This is a sentence
Now let's us take look at the function itself:
char *substrtok_r(char *str, const char *substrdelim, char **saveptr);
The first argument is the source string, the second argument is the delimiters
strings and the third one is doule pointer of char. You have to pass a pointer
to a pointer of char. This will be used to remember where the function should
resume scanning next, more on that later.
This is the algorithm:
if str is not NULL:
start a new scan sequence from str
otherwise
resume scanning from string pointed to by *saveptr
found position of substring_d pointed to by 'substrdelim'
if no such substring_d is found
if the current character of the scanned text is \0
no more substrings to return --> return NULL
otherwise
return the scanned text and set *saveptr to
point to the \0 character of the scanned text,
so that the next iteration ends the scanning
by returning NULL
otherwise (a substring_d was found)
create a new substring_a until the found one
by setting the first character of the found
substring_d to 0.
update *saveptr to the start of the found substring_d
plus it's previous length so that *saveptr
points to the past the delimiter sequence found in substring_d.
return new created substring_a
This first part is easy to understand:
if(str)
haystack = str;
else
haystack = *saveptr;
Here if str is not NULL, you want to start a new scan sequence. That's why
in main the input pointer is set to point to the start of the string saved
in line. Every other iteration must be called with str == NULL, that's
why the first thing is done in the while loop is to set input = NULL; so
that substrtok_r resumes scanning using *saveptr. This is the standard
behaviour of strtok.
The next step is to look for a delimiting substring:
char *found = strstr(haystack, substrdelim);
The next part handles the case where no delimiting substring is
found2:
if(found == NULL)
{
*saveptr = haystack + strlen(haystack);
return *haystack ? haystack : NULL;
}
*saveptr is updated to point past the whole source, so that it points to the
'\0'-terminating byte. The return line can be rewritten as
if(*haystack == '\0')
return NULL
else
return haystack;
which says if the source already is an empy string1, then return
NULL. This means no more substring are found, end calling the function. This
is also standard behaviour of strtok.
The last part
*found = 0;
*saveptr = found + strlen(substrdelim);
return haystack;
is handles the case when a delimiting substring is found. Here
*found = 0;
is basically doing
found[0] = '\0';
which creates substrings as explained above. To make it clear once again, before
Before
*found = 0;
*saveptr = found + strlen(substrdelim);
return haystack;
the memory looks like this:
+-----+-----+-----+-----+-----+-----+
| 'a' | ' ' | '-' | '>' | ' ' | 'b' | ...
+-----+-----+-----+-----+-----+-----+
^ ^
| |
haystack found
*saveptr
After
*found = 0;
*saveptr = found + strlen(substrdelim);
the memory looks like this:
+-----+------+-----+-----+-----+-----+
| 'a' | '\0' | '-' | '>' | ' ' | 'b' | ...
+-----+------+-----+-----+-----+-----+
^ ^ ^
| | |
haystack found *saveptr
because strlen(substrdelim)
is 3
Remember if I do printf("%s\n", haystack); at this point, because the '-' in
found has been set to 0, it will print a. *found = 0 created two strings out
of one like exaplained above. strtok (and my function which is based on
strtok) uses the same technique. So when the function does
return haystack;
the first string in token will be the token before the split. Eventually
substrtok_r returns NULL and the loop exists, because substrtok_r returns
NULL when no more split can be created, just like strtok.
Fotenotes
1An empty string is a string where the first character is already the
'\0'-terminating byte.
2This is very important part. Most of the standard functions in the C
library like strstr will not return you a new string in memory, will
not create a copy and return a copy (unless the documentation says so). The
will return you a pointer pointing to the original plus an offset.
On success strstr will return you a pointer to the start of the substring,
this pointer will be at an offset to the source.
const char *txt = "abcdef";
char *p = strstr(txt, "cd");
Here strstr will return a pointer to the start of the substring "cd" in
"abcdef". To get the offset you do p - txt which returns how many bytes
there are appart
b = base address where txt is pointing to
b b+1 b+2 b+3 b+4 b+5 b+6
+-----+-----+-----+-----+-----+-----+------+
| 'a' | 'b' | 'c' | 'd' | 'e' | 'f' | '\0' |
+-----+-----+-----+-----+-----+-----+------+
^ ^
| |
txt p
So txt points to address b, p points to address b+2. That's why you get
the offset by doing p-txt which would be (b+2) - b => 2. So p points to
the original address plus the offset of 2 bytes. Because of this bahaviour
things like *found = 0; work in the first place.
Note that doing things like txt + 2 will return you a new pointer pointing to
the where txt points plus the offset of 2. This is called pointer arithmetic.
It's like regualr arithmetic but here the compiler takes the size of an object
into consideration. char is a type that is defined to have the size of 1,
hence sizeof(char) returns 1. But let's say you have an array of integers:
int arr[] = { 7, 2, 1, 5 };
On my system an int has size of 4, so an int object needs 4 bytes in memory.
This array looks like this in memory:
b = base address where arr is stored
address base base + 4 base + 8 base + 12
in bytes +-----------+-----------+-----------+-----------+
| 7 | 2 | 1 | 5 |
+-----------+-----------+-----------+-----------+
pointer arr arr + 1 arr + 2 arr + 3
arithmetic
Here arr + 1 returns you a pointer pointing to where arr is stored plus an
offset of 4 bytes.

Related

Why does t point to letter C?

I want to read my string backwards. I did that, but I don't understand how two parts of my code work.
char s1[] = "ABC";
printf("%s", s1);
size_t len = strlen(s1);
printf("\n%d", len);
char *t = s1 + len - 1;
printf("\n%s\n", t);
while (t>=s1)
{
printf("%c", *t);
t = t - 1;
}
First: How does t point to letter C?
Second: How is it possible to add variable len which holds integer with an array that holds literals? Is it because pointer t adds their addresses by using pointer arithmetic?
This
char s1[] = "ABC";
looks like
0x100 0x101 0x102 0x103 . . . .Assume 0x100 is base address of s1
--------------------------------
| A | B | C | \0 |
--------------------------------
s1
Here s1 which is char array, points to base address 0x100(let's assume).
I want to read my string reversely ?
For this you need someone to point to 0x102 location i.e last element of an array, for that
size_t len = strlen(s1); /* finding length of array s1 i.e it returns 3 here */
char *t = s1 + len - 1; /* (0x100 + 3*1) - 1 i.e char pointer t points to 0x102 */
above two lines of code is written. Now it looks like
0x100 0x101 0x102 0x103 . . . .
--------------------------------
| A | B | C | \0 |
--------------------------------
s1 t <-- t points here
Now when you do *t it prints the char value at t location i.e value at 0x102 i.e it prints C, in the next iteration you need to print the char one position back, so for that you are doing t = t - 1;.
Note : Here
char *t = s1 + len - 1;
s1 is char pointer and len is an integer variable, so when you are doing pointer arithmetic it will automatically increment by the size of data being pointed by pointer. For e.g
char *t = s1 + len;
evaluated as
t = 0x100 + 3*sizeof(*s1); ==> 0x100 + 3*1 ==> 0x103
char s1[] = "ABC";
s1 is an array of 4 characters char[4] with values {'A','B','C','\0'}
size_t len = strlen(s1);
s1 "decays" (read: is automagically converted) from an array of type to a pointer to type. So s1 decays from an array of 4 characters into a pointer to the first character of the array.
The strlen counts the number of bytes before encountering the null byte delimiter '\0'. Starting from 'A' we can count 'A', 'B', 'C' - that's len = 3.
Pointers in C are normal integers (ok, on most architectures). You can add to them and substract to them, and use uintptr_t to convert them to an integer. But adding to them without a cast will use "pointer arithmetics", that means that (int*)5 + 2 is to the value equal to 5 + 2 * sizeof(int).
char *t = s1 + len - 1;
s1 decays to the pointer to the first character inside the s1 array, that's 'A'. We add + (len = 3), that means that s1 + 3 points to the byte holding '\0' inside the s1 = (char[4]){'A','B','C','\0'} array. Then we subtract - 1, so t will now point to a byte holding the character 'C' inside the s1 array.
while (t >= s1) {
... *t ...
t = t - 1;
}
Start: s1 points to 'A'. t points to 'C'.
while: t is greater then s1. By two. t - s1 = 2, ie. s1 + 2 = t
loop: *t is equal to 'C'.
decrement: t--, so now t will point to 'B'.
while: t is greater then s1. By onw.
loop: *t is equal to 'B'.
decrement: Then t--, so now t will point to 'A'.
while: Now t is equal to then s1. Both point to the first character of the array.
loop: *t is equal to 'B'.
decrement: Then t--, so now t will point to an unknown location before the array. As pointers
(on most architectures) are simple integers, you can decrement and increment them as normal variables.
while: t is now lower then s1. Loop terminates.
Notes:
printf("\n%d", len); is undefined behavior and spawns nasal demons. Use printf("\n%zu", len); to print a size_t variable.
you can print pointer value by using the %p specifier and casting to void printf("%p", (void*)t)
t = s1 - 1. Assigning a pointer to one element before an array is undefined behavior in C. That happens in the end condition of the loop when t = t - 1. Change to do { .. } while loop.
In the language C arrays are a bit strange. At array-of-x can degrade in to a pointer-to-x, very easily. For example if passing to another routine, or as in your case when adding to it. So you are correct it is pointer arithmetic. (In pointer arithmetic you can add pointers and integers, to get pointers.)

Issue With Comparing Strings In C

I'm trying to compare a string with another string and if they match I want the text "That is correct" to output but I can't seem to get it working.
Here is the code:
int main ()
{
char * password = "Torroc";
char * userInput;
printf("Please enter your password: ");
scanf("%s", userInput);
if (strcmp(password, userInput) == 0) {
printf("That is correct!");
}
}
In your code, userInput pointer does not have provision to hold the string that you are about to pass using the scanf call. You need to allocate space for the cstring userInput in your stack, before you try to save/assign any string to it. So...
You need to change the following code:
char * userInput;
to:
char userInput[200];
Here, 200 is just an arbitrary value. In your case, please select the max. length of the string + 1 for the (\0).
When you enter characters you need to store the characters somewhere.
char* userInput;
is an uninitialized pointer.
So first you declare an array for your input
char userInput[128];
Now when reading from the keyboard you need to make sure the user does not enter more characters than 127 + one for \0 because it would overwrite the stack so best way to read from the keyboard is to use fgets, it also good to check the return value, if the user simply pressed ENTER without writing anything fgets returns NULL.
if (fgets(userInput, sizeof(userInput), stdin) != NULL) {
Now you have the string that the user entered plus the end of line character. To remove it you can do something like
char* p = strchr(userInput,'\n');
if ( p != NULL ) *p = '\0';
Now you can compare the strings
if (strcmp(password, userInput) == 0) {
puts("That is correct!");
}
When you think about "a string" in C, you should see it as an array of char's.
Let me use the identifier s instead of userInput for brevity:
0 1 2 3 4 5 9
+---+---+---+---+---+---+-- --+---+
s -> | p | i | p | p | o | \0| ... | |
+---+---+---+---+---+---+-- --+---+
is what
char s[10] = "pippo";
would create.
In other words, it's a block of memory where the first 6 bytes have been initialized as shown. There is no s variable anywhere.
Instead, declaring a char * like in
char *s;
would create a variable that can hold a pointer to char:
+------------+
s| 0xCF024408 | <-- represent an address
+------------+
If you think this way, you notice immediately that doing:
scanf("%s",s);
only make sense in the first case, where there is (hopefully) enough memory to hold the string.
In the second case, the variable s points to some random address and you will end up writing something into an unknown memory area.
For completeness, in cases like:
char *s = "pippo";
you have the following situation in memory:
0 1 2 3 4 5
+---+---+---+---+---+---+ Somewhere in the
0x0B320080 | p | i | p | p | o | \0| <-- readonly portion
+---+---+---+---+---+---+ of memory
+------------+ a variable pointing
s| 0x0B320080 | <-- to the address where
+------------+ the string is
You can make s pointing somewhere else but you can't change the content of the string pointed by s.

What does this block of C code do in order to find the end character?

char *start = str;
char *end = start + strlen(str) - 1; /* -1 for \0 */
char temp;
How does that find the end of the string? If the string is giraffe, start holds that string, then you have:
char *end = "giraffe" + 7 - 1;
How does that give you the last char in giraffe? (e)
Here's how "giraffe" is laid out in memory, with each number giving that character's index.
g i r a f f e \0
0 1 2 3 4 5 6 7
The last character e is at index 6. str + 6, alternatively written as &str[6], yields address of the last character. This is the address of the last character, not the character itself. To get the character you need to dereference that address, so *(str + 6) or str[6] (add a *, or remove the &).
In English, here are various ways to access parts of the string:
str == str + 0 == &str[0] address of character at index 0
== str + 6 == &str[6] address of character at index 6
*str == *(str + 0) == str[0] character at index 0 ('g')
== *(str + 6) == str[6] character at index 6 ('e')
If the string is giraffe, start holds that string
Not exactly, start is a char *, so it holds a pointer, not a string. It points to the first character of "giraffe": g.
start + 1 is also a char * pointer and it points to the next element of size char, in this case the i.
start + 5 is a pointer to the second f.
start + 6 is a pointer to the e.
start + 7 is a pointer to the special character \0 or NUL, which denotes the end of a string in C.
start is a pointer to the string "giraffe" in memory, not the string itself.
Likewise end is a pointer to the start of the string + 7 bytes (minus one to account for the null terminator).
There is no string type in C, just char, and arrays of char.
I would tell you to google "c strings", but since that's apparently a term that you need safesearch for these days, here's a link: http://www.cprogramming.com/tutorial/lesson9.html

static array of char not filled

I want to fill an array of char, one by one, so I am using the above code for testing, and the final output of "str" will always be the first char entered instead of all char, whats wrong ?
void gime_char(char c)
{
static *str;
static i;
if(i == 0)
str = malloc(sizeof(*str) * 10);
if(c == 'X')
{
printf("full str:%s\n", str);
}
printf("c == %c\n", c);
str[i] = c;
printf("d == %d\n", i);
i++;
}
int main()
{
char c;
while(c != 'X')
{
c = getchar();
gime_char(c);
}
}
The type of static *str is static int *str, but a string consists of chars. So now your string does not end up being stored with the characters adjacent to one another as you would expect, because each element of str has the size of int (probably 4 bytes), not that of char.
This part of the code should be fixed by specifying the type as static char *str. Once you fix that, there will be another problem when printing str without terminating it with a NUL character ('\0').
You're missing a type in the definition of i, and the type in the definition of str is incomplete: you say “pointer” (with the * character) but you don't say to what. For historical reasons, if you omit a type, the compiler assumes you meant int; this is deprecated, and good compilers warn about this.
Since you effectively wrote int *str, the memory layout looks something like this after entering hello (this is machine-dependent, but this is a pretty typical case):
+-----+-----+-----+-----+-----+-----+-----+-----+-----+-----+----
| 'h' | 0 | 0 | 0 | 'e' | 0 | 0 | 0 | 'l' | 0 | ...
+-----+-----+-----+-----+-----+-----+-----+-----+-----+-----+----
^ ^ ^
| | |
str str+1 str+2
Each small cell is one byte (which corresponds to one character). Four cells make up one int. The line
str[i] = c;
writes one int into str. For example, when c is 'h', which has the numerical value 104, the number 104 is written into the int object str[0], which is represented as the four-byte sequence {104, 0, 0, 0}. This happens again for the next character, which is written in the next int-sized slot in the array, meaning 4 bytes further.
In the line
printf("full str:%s\n", str);
you print str as a string. In a string, the first zero byte marks the end of the string. So you see the string "h".
Your machine is little-endian. Exercise: what would you see on a big-endian machine?
The fix is to declare the types properly.
You should also initialize your variables. static variables are initialized to 0 anyway, but it's clearer if you do it explicitly. The variable c is not static, so it starts out containing whichever value was there before in memory; this could happen to be 'X', so you must initialize it explicitly.
Additionally, you need to make sure that the string is terminated by a zero byte before printing it. The static keyword ensures that the str variable is initialized to a null pointer, but the space that the pointer points to is allocated by malloc and contains whatever was there before.
void gime_char(char c)
{
static char *str; /* <<<< */
static int i; /* <<<< */
if(i == 0)
str = malloc(sizeof(*str) * 10);
if(c == 'X')
{
str[i] = 0; /* <<<< */
printf("full str:%s\n", str);
}
printf("c == %c\n", c);
str[i] = c;
printf("d == %d\n", i);
i++;
}
int main()
{
char c = 0; /* <<<< */
while(c != 'X')
{
c = getchar();
gime_char(c);
}
return 0; /* <<<< */
}
Advices :
Check that malloc didn't return an error
i is not initialize
Type of *str is wrong (static char *str)
Before using %s you have to add a '\0' at the end of your string.
I would say your problem comes from fact that you declare static *str;.
You declare it with out specifying the type! Compilers pass with, with a warning that this implies an int. So basically you end up with a static pointer to int. Which is not meant to store ANSI strings.
Later you allocate space for the buffer (I suppose) with str = malloc(sizeof(*str) * 10);. This is also wrong, because you allocate space for 10 pointers to str.
You want to work with characters.
static char *str;
if(i == 0)
str = malloc(sizeof(char) * 10);
Also you should initialize the string to zeros as it is almost certain you will get some garbage there and ANSI string is expected to be NULL terminated. Preferably i too but compilers initialize variables on stack.

somebody please explain about strings in c?

how to store two strings one after other without concatenation (we can increment the address)
char str[10];
scanf("%s",str);
str=str+9;
scanf("%s",str);
NOTE: Here if I give first string as BALA and 2nd as HI, it should print as HI after BALA . But HI should not replace BALA.
You cannot increment (or change in any other way) an array like that, the array variable (str) is a constant which cannot be changed.
You can do it like so:
char str[64];
scanf("%s", str);
scanf("%s", str + strlen(str));
This will first scan into str, then immediately scan once more, starting the new string right on top of the terminating '\0' of the first string.
If you enter "BALA" first, the beginning of str will look like this:
+---+---+---+---+----+
str: | B | A | L | A | \0 |
+---+---+---+---+----+
and since strlen("BALA") is four, the next string will be scanned into the buffer starting right on top of the '\0' visible above. If you then enter "HI", str will start like so:
+---+---+---+---+---+---+----+
str: | B | A | L | A | H | I | \0 |
+---+---+---+---+---+---+----+
At this point, if you print str it will print as "BALAHI".
Of course, this is very dangerous and likely to introduce buffer overrun, but that's what you wanted.
If I understand what you want to do correctly perhaps you want to put the strings in an array.
So a modified version of your code would look something like
char strings[ARRAY_LENGTH][MAX_STRING_LENGTH];
char* str = strings[0];
scanf("%s",str);
str=strings[1];
scanf("%s",str);
Then to print all the strings you would have to loop over the array like this
int i;
for(i = 0; i < ARRAY_LENGTH; i++)
{
printf(strings[i]);
}
(you would have to define ARRAY_LENGTH and MAX_STRING_LENGTH)
Moving in a similar direction to unwind, you can use the %n directive to determine how many bytes have been read. Don't forget to subtract any leading whitespace. You may also want to read your manual regarding scanf very carefully, but paying particular care to the "RETURN VALUE" section. Handling the return value is necessary to ensure a string was actually read and avoid undefined behaviour.
char str[64];
int whitespace_length, str_length, total_length;
/* NOTE: Don't handle errors with assert!
* You should replace this with proper error handling */
assert(scanf(" %n%s%n", &whitespace_length, str, &total_length) == 1);
str_length = total_length - str_length;
assert(scanf(" %n%s%n", &whitespace_length, str + str_length, &total_length) == 1);
str_length += total_length - str_length;
May be you are looking at some thing like this
char arr[100] = {0,}, *str = NULL;
/** initial String will be scanned from beginning **/
str = arr;
/** scan first string **/
fgets(str, 100, stdin);
/** We need to replace NULL termination with space is space is delimiter **/
str += strlen(str)-1;
*str = ' ' ;
/** scan second string from address just after space,
we can not over ride the memory though **/
fgets(str, 100 - strlen(str), stdin);
printf("%s",arr);
Well incase you need the same with scanf
char arr[100] = {0,}, *str = NULL;
/** initial String will be scanned from beginning **/
str = arr;
/** scan first string **/
scanf("%s",str);
/** We need to replace NULL termination with space is space is delimiter **/
str += strlen(str);
*str = ' ' ;
/** scan second string from address just after space,
* we can not over ride the memory though **/
str++;
scanf("%s",str);
printf("%s",arr);

Resources