I'm learning c and I have a problem with the following code. I want to convert "Hello" to "H*llo". But the code does not work.
The code does not give an error and does not work.
#include <stdio.h>
int length(char *abc){
int i;
for (i = 0; i < abc[i]; i++);
return i;
}
int hideAfromB(char *a, char *b){
int n = 0;
int aLength = length(a);
int bLength = length(b);
for (int i = 0; i < bLength; i++){
if (a[0+n] == b[i]){
n = n + 1;
if (n == aLength){
for (int j = 0; j < aLength; j++)
{
b[i-j] = '*';
}
n = 0;
}
}
else{
n = 0;
}
}
printf("%s",b);
return 0;
}
int main()
{
hideAfromB("e","Hello");
return 0;
}
I need help.
Thanks.
Because the string "Hello" is a constant and you can't change it.
As other have stated, declaring explicitly a char array will sove the problem:
#include <stdio.h>
#include <string.h>
int length(char *abc){
int i;
for (i = 0; i < abc[i]; i++);
return i;
}
int hideAfromB(char *a, char *b){
int n = 0;
int aLength = strlen(a);
int bLength = strlen(b);
for (int i = 0; i < bLength; i++){
if (a[0+n] == b[i]){
n = n + 1;
if (n == aLength){
for (int j = 0; j < aLength; j++)
{
b[i-j] = '*';
}
n = 0;
}
}
else{
n = 0;
}
}
printf("%s",b);
return 0;
}
int main()
{
char t [] = "Hello";
hideAfromB("e",t);
return 0;
}
Link to the fixed code:
The main issue is that the second argument in hideAfromB("e","Hello"); is a constant string which can not be modified.
for (i = 0; i < abc[i]; i++);
This literally iterates through the array until the iterator value is bigger than the value in the array while executing an empty instruction (;).
size_t is the proper type for string length.
You could use strstr to find a single character in a string.
#include <stdio.h>
#include <string.h>
int length(char *abc){
for (int i = 0; i >= 0; i++) {
if (abc[i] == '\0') {
return i;
}
}
return -1; // indicate string end not found
}
int hideAfromB(char *a, char *b){
int n = 0;
size_t aLength = strlen(a); // standard function
int bLength = length(b); // modified own function
for (size_t i = 0; i < bLength; i++){
if (a[n] == b[i]){
n = n + 1;
if (n == aLength){
for (int j = 0; j < aLength; j++)
{
b[i-j] = '*';
}
n = 0;
}
}
else{
n = 0;
}
}
printf("%s\n",b);
return 0;
}
int main()
{
char hello[] = "Hello"; // the elements of the array can be modified
hideAfromB("e", hello);
return 0;
}
$ gcc -Wall compare.c
$ ./a.out
H*llo
$
Related
I need to write a program that iterates through all possible combinations for a base-2 (binary) vector. If the size of this vector is 3 you can do this with three nested loops, like this:
bool array[3];
for(int i = 0; i < 2; i++)
{
for(int j = 0; j < 2; j++)
{
for(int k = 0; k < 2; k++)
{
array[0] = i;
array[1] = j;
array[2] = k;
}
}
}
But the problem is that in my application, the array size is variable and can basically be any number. If I'm looking to find all values of a 12-bit vector, I don't want to write 12 nested loops and so it is not maintainable to use the code above. Instead I have come up with the following solution:
#include <stdio.h>
#include <stdlib.h>
#include <stdbool.h>
#include <math.h>
#define SIZE 12
int main(void)
{
bool array[SIZE];
for(int i = 0; i < SIZE; i++) array[i] = 1;
int max_num = pow(2, SIZE);
for(int i = 0; i < max_num; i++)
{
if(array[0] == 0) array[0]++;
else
{
array[0] = 0;
for(int j = 1; j < SIZE; j++)
{
if(array[j] == 1) array[j] = 0;
else
{
array[j] = 1;
break;
}
}
}
for(int j = 0; j < SIZE; j++)
{
printf("%d", array[j]);
if(j != SIZE - 1) printf(", ");
else printf("\n");
}
}
}
This still seems as a lot of code to me for such a relatively simple thing. My question is: is there a more efficient way to do this?
What you are doing with the array is effectively incrementing (adding one) to the number represented by the array.
Let's leave the incrementing to the compiler and use bits from the integer.
#include <stdio.h>
#include <stdlib.h>
#include <stdbool.h>
#define SIZE 12
int main(void)
{
bool array[SIZE];
int max_num = 1 << SIZE;
for(int i = 0; i < max_num; i++)
{
for(int j = 0; j < SIZE; j++)
{
array[j] = (i >> j) & 1;
}
for(int j = 0; j < SIZE; j++)
{
printf("%d", array[j]);
if(j != SIZE - 1) printf(", ");
else printf("\n");
}
}
}
As pointed out by others, it is essentially incrementing a binary number. However, in keeping with the spirit of the original code, I decided not to "cheat" by using native addition/increment operators to increment the vector, and came up with the following:
#include <stddef.h>
#include <stdbool.h>
bool first(size_t size, bool array[size])
{
size_t i;
for (i = 0; i < size; i++)
{
array[i] = 0;
}
return i > 0;
}
bool next(size_t size, bool array[size])
{
size_t i;
for (i = 0; i < size && array[i]; i++)
{
array[i] = 0;
}
if (i < size)
{
array[i] = 1;
return 1;
}
return 0;
}
#include <stdio.h>
int main(void)
{
enum { SIZE = 12 };
bool array[SIZE];
bool going;
for (going = first(SIZE, array); going; going = next(SIZE, array))
{
size_t i;
for (i = 0; i < SIZE - 1; i++)
{
printf("%d, ", array[i]);
}
printf("%d\n", array[i]);
}
return 0;
}
It could be adapted to work in other bases easily:
#include <stddef.h>
#include <stdbool.h>
bool first(size_t size, unsigned int array[size])
{
size_t i;
for (i = 0; i < size; i++)
{
array[i] = 0;
}
return i > 0;
}
bool next(size_t size, unsigned int array[size], unsigned int base)
{
size_t i;
for (i = 0; i < size && array[i] == base - 1; i++)
{
array[i] = 0;
}
if (i < size)
{
array[i]++;
return 1;
}
return 0;
}
#include <stdio.h>
int main(void)
{
enum { SIZE = 5 };
enum { BASE = 3 };
unsigned int array[SIZE];
bool going;
for (going = first(SIZE, array); going; going = next(SIZE, array, BASE))
{
size_t i;
for (i = 0; i < SIZE - 1; i++)
{
printf("%u, ", array[i]);
}
printf("%u\n", array[i]);
}
return 0;
}
Given two arrays: int nums[N] and int *ptrs[N] (N is a constant number).
I have to initialize the first array with some numbers. After that, i have to initialize the second array, so every element of the second array points to the element with the same index of the first array. (ptrs[0] points to nums[0],...).
Now i have to write a function with "ptrs" as argument that modifies the pointers in such a way that the first element of the second array points to the smallest number in the first array,..)
It's not allowed to change the "nums-array", i can only change the "ptrs-array".
This is my code i already have, but when i run it, the "nums-array" changes too.
What do i do wrong?
#include <stdio.h>
#define N 6
void sort(int *ptrs);
int main()
{
int nums[N] = { 1,6,7,8,2,5 };
int(*ptrs)[N];
int i;
ptrs = nums;
sort(ptrs);
for (i = 0; i < N; i++)
printf("nummer is: %d en %d\n", (*ptrs)[i], nums[i]);
return 0;
}
void sort(int *ptrs)
{
int i, j, tmp;
for (i = 0; i < N; i++)
for (j = i + 1; j < N; j++)
if ((ptrs)[i] > (ptrs)[j])
{
tmp = (ptrs)[i];
(ptrs)[i] = (ptrs)[j];
(ptrs)[j] = tmp;
}
}
Fix for the first part:
int main()
{
int nums[N] = { 1,6,7,8,2,5 };
int *ptrs[N]; // fix
int i;
for(i = 0; i < N; i++) // fix
ptr[i] = nums+i; // fix (or ptr[i] = &nums[i])
I found the solution, thanks for helping guys!
#include <stdio.h>
#define N 6
void sort(int ptrs[], int nums[]);
int main()
{
int nums[N] = { 1,6,7,8,2,5 };
int i,j,*p, *ptrs[N];
for (i = 0; i < N; i++) {
ptrs[i] = &nums[i];
}
sort(ptrs, nums);
return 0;
}
void sort(int *ptrs[], int nums[])
{
int i, j, tmp, p[N];
for (i = 0; i < N; i++)
p[i] = *ptrs[i];
for(j = 0; j < N; j++)
for (i = 0; i <= N; i++)
if (p[i] > p[i+1])
{
tmp = (ptrs)[i];
(ptrs)[i] = (ptrs)[i+1];
(ptrs)[i+1] = tmp;
for (i = 0; i < N; i++)
p[i] = *ptrs[i];
}
for (i = 0; i < N; i++)
printf("nummer is: %d en %d\n", *ptrs[i], nums[i]);
return;
}
Why this code is giving segmentation fault error?
This is code using for loop for left shift the given array at stdin by no of rotations.
#include <stdio.h>
#include <string.h>
#include <math.h>
#include <stdlib.h>
int *rotatebyone(int *array_input, int len_of_arr);
void rotate(int *array_input, int len_of_arr, int no_of_rota);
int main()
{
int array1[] = { };
int array2[] = { };
int array3[] = { };
int i = 0, j = 0, size_of_arr = 0, no_of_rotations = 0;
for (i = 0; i < 2; i++)
{
scanf("%d", &array1[i]);
//printf("%d", array1[i]);
}
size_of_arr = array1[0];
no_of_rotations = array1[1];
for (i = 0; i < size_of_arr; i++)
{
scanf("%d", &array2[i]);
//printf("%d ", array2[i]);
}
rotate(array2, size_of_arr, no_of_rotations);
return 0;
}
void rotate(int *array_input, int size_of_array, int no_of_rota)
{
int h = 0;
for (h = 0; h < no_of_rota; h++)
{
rotatebyone(array_input, size_of_array);
}
for (h = 0; h < size_of_array; h++)
printf("%d ", array_input[h]);
}
int *rotatebyone(int *array_input1, int len_of_arr)
{
//int array3 = {};
int j = 0, k = 0;
int temp = 0;
temp = array_input1[0];
for (k = 0; k < len_of_arr - 1; k++)
{
array_input1[k] = array_input1[k + 1];
}
array_input1[len_of_arr - 1] = temp;
return array_input1;
}
For array2[], you have not mentioned its size. It can be evn 1000 or 10000. Better use int * array2 and allot memory through malloc.
Reg array1, it can be initialesed as int array1[2] since we know two elements are there for array1.
my output values
#include <stdio.h>
#include <stdlib.h>
#include <stdbool.h>
#define W 160
#define H 105
struct dungeons {
int x;
int y;
int width;
int height;
};
void randomNumberGenerator(int seed);
void makeGameBoard(int gameBoard[W][H]);
void makeDungeonRooms(struct dungeons d[10]);
void printGame(int gameBoard[W][H]);
int main(int argc, char *argv[]) {
int gameBoard[W][H];
//int gameBoard[160][105] = {2};
struct dungeons d[10];
makeGameBoard(gameBoard);
makeDungeonRooms(d);
printGame(gameBoard);
return 0;
}
void randomNumberGenerator(int seed) {
srand(seed);
}
void makeGameBoard(int gameBoard[160][105]) {
int i;
int j;
for (j = 0; j < 105; j++) {
for (i = 0; i < 160; i++) {
gameBoard[i][j] = 2;
//gameBoard[i][j] = 2;
/*
if (j == 0) {
gameBoard[i][j] = 2;
} else
if (j == 104) {
gameBoard[i][j] = 2;
} else
if (i == 0) {
gameBoard[i][j] = 2;
} else
if (i == 159) {
gameBoard[i][j] = 2;
} else {
gameBoard[i][j] = 4;
}
*/
}
}
gameBoard[0][1] = 2;
gameBoard[0][0] = 2;
gameBoard[159][0] = 3;
}
void makeDungeonRooms(struct dungeons d[10]) {
int i;
for (i = 0; i < W; i++) {
d[i].x = 0;
d[i].y = 0;
d[i].width = 0;
d[i].height = 0;
}
}
void printGame(int g[W][H]) {
int i;
int j;
for (i = 0; i < W; i++) {
for (j = 0; j < H; j++) {
printf("%d", g[i][j]);
/*
if (g[i][j] == 2) {
printf("|");
} else
if (g[i][j] == 1) {
printf("X");
} else {
printf(" ");
}
*/
}
printf("\n");
}
}
I'm making a grid. But the first 5 rows and half of the 6th row, when printed output the value 0. I'm setting everything to 2 in the for loop, and even after when I try to manually change the value, it still doesn't. The last one [159][0] works but nothing in the first 5 rows and half of the 6th seem to work. They stay 0. Why?
The problem is here:
void makeDungeonRooms(struct dungeons d [10]){
int i;
for(i = 0; i< W; i++){
d[i].x = 0;
d[i].y = 0;
d[i].width = 0;
d[i].height = 0;
}
}
where #define W 160. Accessing array out of bound can trigger undefined behavior. It can trigger a segmentation fault, it can remain unnoticed for a long time or alter the output of the program in very strange ways. Here, zeroing the dungeons also partly zeroed the gameBoard. Keep it that way: your game is going to be hilarious!
I've made an array that is between [0,1000], and I've printed it. Next step is to arrange the array using switch statements into five different cases 0 to 199, etc. When trying to do so the for loop won't stop. I tried putting a printf after countOne in case 1, no printout occurs either.
Any suggestions
Thanks for your help
#include <stdio.h>
#include <stdlib.h>
#include <math.h>
int n;
int arraySize;
int randN;
int rand();
int countOne = 0;
int countTwo = 0;
int countThree = 0;
int countFour = 0;
int countFive = 0;
int countSix = 0;
int *p;
int *p1;
int main()
{
printf("What is the size of the array\n");
scanf("%d", &n);
//MAKING THE N-size ARRAY
int array[n];
int i;
for (i = 0; i < n; i++) {
randN = rand() % 999;
array[i] = randN;
p = (int*)malloc(i * sizeof(int));
p[i] = array[i];
}
//SORTING THE N-size ARRAY
for (i = 0; i < n; i++) {
printf("%i\n", array[i]);
}
p = (int*)malloc(sizeof(int));
p1 = (int*)malloc(5 * sizeof(int));
p1[0] = countOne;
p1[1] = countTwo;
for (i = 0; i < n; i++) {
switch (i) {
case 1:
for (i = 0; array[i] >= 0 && array[i] <= 199; i++) {
countOne++;
}
case 2:
for (i = 0; array[i] >= 200 && array[i] <= 399; i++) {
countTwo++;
return countTwo;
}
}
}
}
HERE IS MY CODE AS OF CURRENT:
#include <stdio.h>
#include <stdlib.h>
#include <math.h>
int main()
{
int n;
int arraySize;
int randN;
int rand();
int countOne = 0;
int countTwo = 0;
int countThree = 0;
int countFour = 0;
int countFive = 0;
int countSix = 0;
int *p;
int *p1;
printf("What is the size of the array\n");
scanf("%d", &n);
//MAKING THE N-size ARRAY
int array[n];
int i;
for (i = 0 ; i < n; i++ )
{
randN=rand() % 999;
array[i]=randN;
p=(int*)malloc(i*sizeof(int));
p[i]= array[i];
}
//PRINTING THE N-size ARRAY
for (i = 0; i < n; i++)
{
printf("%i\n", array[i]);
}
//SORTING THE N-size ARRAY
int j;
for (j = 0 ; j < n ; j++)
{
switch(j)
{
case 1:
for(i = 0 ; array[i] >= 0 && array[i] <= 199; i++)
{
countOne++;
return countOne;
}
case 2:
for(i = 0 ; array[i] >= 200 && array[i] <= 399; i++)
{
countTwo++;
return countTwo;
}
}
}
HERE IS THE PRINT OUT:
What is the size of the array
3
823
7
347
There is 0 integers between 0 and 199
There is 0 integers between 200 and 399
The program has many problems.
Here is a simpler version:
#include <stdio.h>
#include <stdlib.h>
int compare_ints(const void *a, const void *b) {
const int *pa = a, *pb = b;
return (*pa > *pb) - (*pa < *pb);
}
int main(void) {
int i, n;
int stats[5] = { 0, 0, 0, 0, 0 };
printf("What is the size of the array?\n");
scanf("%d", &n);
//MAKING THE N-size ARRAY
int *array = malloc(n * sizeof(int));
int *saved = malloc(n * sizeof(int));
if (array == NULL || saved == NULL) {
printf("cannot allocate arrays\n");
exit(1);
}
for (i = 0; i < n; i++) {
int randN = rand() % 999;
saved[i] = array[i] = randN;
stats[randN / 200] += 1;
}
printf("initial array contents:\n);
for (i = 0; i < n; i++) {
printf("%i\n", array[i]);
}
printf("\n");
//SORTING THE N-size ARRAY
qsort(array, n, sizeof(*array), compare_ints);
printf("sorted array:\n);
for (i = 0; i < n; i++) {
printf("%i\n", array[i]);
}
printf("\n");
for (i = 0; i < 5; i++) {
printf("%d values between %d and %d\n", stats[i], i * 200, (i + 1) * 200 - 1);
}
printf("\n");
// do whatever else you are supposed to with array and saved
//...
free(array);
free(saved);
return 0;
}