Splitting an Array in C - c

Suppose I have an array and I want to remove elements from certain ranges of indices.
If I know ahead of time the size of the array, the size of every element in the array, and what ranges of indices I want to remove is there any way I can avoid copying over a new array?

If you don't want to use a new array for copying , you can think of doing this in the same array itself , here is what I have :
#include<stdio.h>
#include<string.h>
int main()
{
char str[] = "hello world";
int i , strt , end , j;
setbuf ( stdout , NULL );
printf ("enter the start and end points of the range of the array to remove:\n");
scanf ("%d%d", &strt , &end);
int len = strlen (str);
for ( i = end; i >= strt ;i--)
{
str[i-1] = str[i];
for ( j = i+1; j <= len ; j++)
{
str[j-1] = str[j];
}
len--;
}
printf ("%s" , str);
return 0;
}
While this code is for character arrays, you can also use the algorithm for integer arrays with slight modifications (do it as exercise ).
NOTE:- This method is not very efficient though , as you can see the exponential increase in the complexity , so my advice would be just to use the copying over new array method .

Hello you could do something like that.
int main(int ac, char **av)
{
char *str;
int i;
i = 0;
str = strdup("Hello World");
while(str[i])
{
if(i == 6) // 6 = W the range of the array you want to remove
str[i] = '\0';
i++;
}
printf("%s\n", str);
}
The output will be "Hello" instead of "Hello World".

Related

Print array of strings vertically

I know how to print a single string vertically.
char test[100] = "test";
int i;
for(i=0;i<strlen(test);i++){
printf("%c\n",test[i]);
}
Which will give me:
t
e
s
t
But how can I print an array of strings vertically? For example:
char listOfTest[2][10] = {"testing1","quizzing"};
So it can return:
tq
eu
si
tz
iz
gi
1g
Simply loop through the first string and print each character at index i in the first string and the second string till you reach the null terminator of first string
NOTE: this only work when string 1 and string2 are equal in length and will need modification for other test cases
#include <stdio.h>
int main(void)
{
char listOfTest[2][10] = {"testing1","quizzing"};
int i = 0;
//loop through string 1 till NULL is reach
while (listOfTest[0][i])
{
//prints char at index i in string 1 and 2
printf("%c%c\n", listOfTest[0][i], listOfTest[1][i]);
//increment the index value
i++;
}
return (0);
}
Simply print a character from both strings.
(Better to test for the null character rather than repeatedly call strlen().)
for(i = 0; listOfTest[0][i] && listOfTest[1][i]; i++) {
printf("%c%c\n", listOfTest[0][i], listOfTest[1][i]);
}
To extend to n strings ...
size_t num_of_strings = sizeof listOfTest/sizeof listOfTest[0];
bool done = false;
for (size_t i = 0; listOfTest[0][i] && !done; i++) {
for (size_t n = 0; n < num_of_strings; n++) {
if (listOfTest[n][i] == '\0') {
done = true;
break;
}
printf("%c", listOfTest[n][i]);
}
printf("\n");
}

C allocation memory error. Don't find something like this

Could you help please ?
When I execute this code I receive that:
AAAAABBBBBCCCCCBBBBBCOMP¬ıd┐╔ LENGTH 31
There are some weirds characters after letters, while I've allocate just 21 bytes.
#include <stdio.h>
#include <stdlib.h>
char * lineDown(){
unsigned short state[4] = {0,1,2,1};
char decorationUp[3][5] = {
{"AAAAA"},{"BBBBB"},{"CCCCC"}
};
char * deco = malloc(21);
int k;
int p = 0;
for(int j = 0; j < 4; j++){
k = state[j];
for(int i = 0; i < 5; i++){
*(deco+p) = decorationUp[k][i];
p++;
}
}
return deco;
}
int main(void){
char * lineDOWN = lineDown();
int k = 0;
char c;
do{
c = *(lineDOWN+k);
printf("%c",*(lineDOWN+k));
k++;
}while(c != '\0');
printf("LENGTH %d\n\n",k);
}
The function does not build a string because the result array does not contain the terminating zero though a space for it was reserved when the array was allocated.
char * deco = malloc(21);
So you need to append the array with the terminating zero before exiting the function
//...
*(deco + p ) = '\0';
return deco;
}
Otherwise this do-while loop
do{
c = *(lineDOWN+k);
printf("%c",*(lineDOWN+k));
k++;
}while(c != '\0')
will have undefined behavior.
But even if you will append the array with the terminating zero the loop will count the length of the stored string incorrectly because it will increase the variable k even when the current character is the terminating zero.
Instead you should use a while loop. In this case the declaration of the variable c will be redundant. The loop can look like
while ( *( lineDOWN + k ) )
{
printf("%c",*(lineDOWN+k));
k++;
}
In this case this call
printf("\nLENGTH %d\n\n",k);
^^
will output the correct length of the string equal to 20.
And you should free the allocated memory before exiting the program
free( lineDOWN );
As some other wrote here in their answers that the array decorationUp must be declared like
char decorationUp[3][6] = {
{"AAAAA"},{"BBBBB"},{"CCCCC"}
};
then it is not necessary if you are not going to use elements of the array as strings and you are not using them as strings in your program.
Take into account that your program is full of magic numbers. Such a program is usually error-prone. Instead you should use named constants.
In
char decorationUp[3][5] = {
{"AAAAA"},{"BBBBB"},{"CCCCC"}
};
your string needs 6 characters to also place the null char, even in that case you do not use them as 'standard' string but only array of char. To get into the habit always reverse the place for the ending null character
you can do
char decorationUp[3][6] = {
{"AAAAA"},{"BBBBB"},{"CCCCC"}
};
Note it is useless to give the first size, the compiler counts for you
Because in main you stop when you read the null character you also need to place it in deco at the end, so you need to allocate 21 for it. As before you missed the place for the null character, but here that produces an undefined behavior because you read after the allocated block.
To do *(deco+p) is not readable, do deco[p]
So for instance :
char * lineDown(){
unsigned short state[] = {0,1,2,1};
char decorationUp[][6] = {
{"AAAAA"},{"BBBBB"},{"CCCCC"}
};
char * deco = malloc(4*5 + 1); /* a formula to explain why 21 is better than 21 directly */
int k;
int p = 0;
for(int j = 0; j < 4; j++){
k = state[j];
for(int i = 0; i < 5; i++){
deco[p] = decorationUp[k][i];
p++;
}
}
deco[p] = 0;
return deco;
}

Is there any proper way how to put integer into string? [C]

I have code like this:
char str[100];
int r = 0;
for(int k = 0; k < i;k++){
str[r++] = y[k];
sprintf(str[r], str, x[k]);
r++;
}
I want in array y I have only alphabetic characters(e.g C,D...) and in array x I have only numbers. I want to make string like "C50D80E20" etc."
But I dont know how to put interger into string(I know I´m using sprintf wrong and also that it shouldn´t be used in this case).
Thanks in advance.
Here you are.
#include <stdio.h>
int main(void)
{
enum { N = 100 };
char s[N];
char a[] = "CDE";
int b[] = { 50, 80, 20 };
int pos = 0;
for ( size_t i = 0; i + 1 < sizeof( a ); i++ )
{
pos += sprintf( s + pos, "%c%d", a[i], b[i] );
}
s[pos] = '\0';
puts( s );
return 0;
}
The program output is
C50D80E20
This statement
s[pos] = '\0';
is required only in the case when there are no values to append to the array s that is when none call of sprintf was executed.
If you want to get a string like this
C50 D80 E20
then just write for example
pos += sprintf( s + pos, "%c%d%c", a[i], b[i], ' ' );
And if you want to remove the last space character then instead of
s[pos] = '\0';
write
s[ pos == 0 ? pos : pos - 1 ] = '\0';
Instead of the function sprintf you could use the function snprintf. But it does not resolve the problem if you allocated not enough memory for the result string because in any case you will not get the expected result in such a case.
As for the function itoa then it is not a standard C function.
Use itoa().
Somthing like that:
itoa(y[k], str[r++], 10);
Here's a link about itoa().
UPDT:
Or as correctly commentator marked - you can use int + '0'
Is there any proper way how to put integer into string? [C]
Use snprintf().
Check results.
char str[N];
int len = snprintf(str[r], sizeof str, "%d", x[k]);
if (len < 0 || (unsigned)len >= sizeof str) Handle_Error();

How to get the length of this array without strlen(), sizeof(arr) / sizeof(arr[0]); does not work, C language

This program, tokenizes a user input string, removes extra spaces and saves each word into a 2D array and then print the tokens
EXAMPLE:
input: " Hello world string house and car"
output and EXPECTED output:
token[0]: Hello
token[1]: world
token[2]: string
token[3]: house
token[4]: and
token[5]: car
THE PROBLEM:
the problem is that I achieved this by using strlen() function when printing the tokens(code located at the very bottom), I am not supposed to use any other library than stdio.h and stdlib.h, since strlen() function is defined in string.h i tried to use sizeof(arr) / sizeof(arr[0]); but it does not work as I want, the result using sizeof is :
token[0]: Hello
token[1]: world
token[2]: string
token[3]: house
token[4]: and
token[5]: car
�oken[6]: ��
token[7]: �
token[8]: ����
token[9]: �
token[10]:
I WOULD LIKE TO HAVE THE EXPECTED OUTPUT WITHOUT USING STRLEN()
#include<stdio.h>
#include <stdlib.h>
#define TRUE 1
char tokenize(char *str, char array[10][20])
{
int n = 0, i, j = 0;
for(i = 0; TRUE; i++)//infinite loop until is the end of the string '\0'
{
if(str[i] != ' '){
//position 1, char 1
array[n][j++] = str[i];// if, it is not space, we save the character
}
else{
array[n][j++] = '\0';//end of the first word
n++;// position for next new word
j=0;// start writting char at position 0
}
if(str[i] == '\0')
break;
}
return 0;
}
//removes extra spaces
char* find_word_start(char* str){
/*also removes all extra spaces*/
char *result = (char*) malloc(sizeof(char) *1000);
int c = 0, d = 0;
// no space at beginning
while(str[c] ==' ') {
c++;
}
while(str[c] != '\0'){ // till end of sentence
result[d++] = str[c++]; //take non-space characters
if(str[c]==' ') { // take one space between words
result[d++] = str[c++];
}
while(str[c]==' ') { //
c++;
}
}
result[d-1] = '\0';
//print or return char?
return result;
free(result);
}
int main()
{
char str[]=" Hello world string dudes and dudas ";
//words, and chars in each word
char arr[10][20];
//call the method to tokenize the string
tokenize(find_word_start(str),arr);
int row = sizeof(arr) / sizeof(arr[0]);
/*----------------------------------------------------------------------*/
/*----------------------------------------------------------------------*/
for(int i = 0;i <= strlen(arr);i++)
/*----------------------------------------------------------------------*/
/*----------------------------------------------------------------------*/
printf("token[%d]: %s\n", i, arr[i]);
return 0;
}
Your code using strlen() may appear the work in this instance but it is not correct.
strlen(arr) makes no semantic sense because arr is not a string. It happens in this case to return 5 because arr has the same address as arr[0], then you kludged it to work for the 6 word output by using the test i <= strlen(arr) in the for loop. The two values strlen(arr) and the number of strings stored in arr are not related.
The expression sizeof(arr) / sizeof(arr[0]) determines the run-time constant number arrays within the array of arrays arr (i.e. 10), not the number of valid strings assigned. It is your code's responsibility to keep track of that either with a sentinel value such as an empty string, or by maintaining a count of strings assigned.
I suggest you change tokenize to return the number of strings (currently it is inexplicably defined to return a char, but in fact only ever rather uselessly returns zero):
int tokenize( char* str, char array[][20] )
{
...
return n ;
}
Then:
int rows = tokenize( find_word_start(str), arr ) ;
for( int i = 0; i < rows; i++ )
{
printf( "token[%d]: %s\n", i, arr[i] ) ;
}

Reversing a string without using any libraries

Now I want to implement a function to "reverse" a given string. My idea was not to swap, rather I thought of declaring a new array in the implemented function to absorb the new string in its reversed state.
Here is the code:
#include <stdio.h>
#include <stdlib.h>
void reverseString( char string[ ], int size );
int main()
{
char string[ 14 ] = "reverse me";
printf( "The string is: %s\n", string );
reverseString( string, 14 );
return 0;
}
void reverseString( char string[ ], int size )
{
int i, j;
char newString[ size ];
for( ( i = ( size ) ) & ( j = 0 ); ( i >= 0 ) && ( j < ( size ) ); i-- & j ++ )
{
newString[ j ] = string[ i ];
}
printf( "\nThe string reversed: %s\n", newString );
}
could anybody please help me to get the idea of reversing strings? Was I approaching the idea when looking at my code or what ?!
function reverseString(string) {
var splitedString = string.split("");
var reverseArray = splitedString.reverse();
var joinArray = reverseArray.join("");
return joinArray;
}
var newString = reverseString("hello");
console.log(newString);
Are you expecting something like this?
A String can be referred to as an array of characters with a null character '\0' at the end of it. If a string is "Banana", then actually the compiler treats it as "Banana\0". When dealing with strings in the program, you have to remember to append the null character to the string that you create.
Here is the working code for the same -
#include <stdio.h>
int main()
{
char string[10] = "banana";
char reverse[10];
int start, end, length = 0;
// Calculating string length - to be used when length is not already known
/*while (string[length] != '\0')
length++;*/
//in this case
length=10;
end = length - 1; /*this is done because indexing in arrays and strings starts
at 0, not at 1...so string[0] gives first character of the
string and string[size-1] gives the last character of the
string*/
for (start = 0; start < length; start++)
{
reverse[start] = string[end];
end--;
}
reverse[start] = '\0'; //here we add the null character to the end of the string
printf("%s\n", reverse);
return 0;
}
Looking at your code, your idea was correct. You just need to brush up some concepts like String indexing, Null character in strings etc.
The same thing can be done using library functions as well.

Resources