How to increment a variable when strstr finds the specified string - c

I'm wanting to have my variable houseTot increment by one every time strstr finds a string with "house" in it. I've essentially done this in my code:
struct Owner1_def
{
int totProps;
char type[40];
float monthlyPrice;
float maintenance;
int bedrooms;
int bathrooms;
};
typedef struct Owner1_def Owner1;
int main(void)
{
char *ptr;
int i = 0;
ptr = strstr(database[i].hometype, "house");
for(i = 0; i <= 3; ++i)
{
if (ptr != NULL)
houseTot++;
}
return 0;
}
But when the program prints houseTot's value, it's still at it's initialized value 0. I don't know much about strstr, but from what I've read, this should work.

The call to strstr() should be moved inside the loop so that the value stored in database[i].hometype can be checked on each iteration:
for(i = 0; i <= 3; ++i) {
ptr = strstr(database[i].hometype, "house");
if (ptr != NULL)
houseTot++;
}
Note that posted code has no definition for the array of structs database[], and the struct provided has no hometype field.

Related

Counting # of index of undefined char array in C

I'm trying to count the number of indexes of an undefined char array which is used as a parameter in the function.
I am already aware that if my array was fixed I can use "sizeof", which isn't the case here.
Attempt:
int counting(char *name3) {
int count = 0;
int i;
//I have no idea what to put as my condition nor do I believe
//I am approaching this situation correctly...
for (i = 0; i < sizeof(name3); i++) {
if (name3[i] != '\0') {
count++;
}
}
return count;
}
Then if it is run by the following code
int main(void) {
char *name = "Lovely";
int x = counting(name);
printf ("The value of x = %d", x);
Prints: The value of x = 0
Any help or pointers would be amazing. Thank you in advance.
In C, Every string ends with '\0' (Null Character)
You can iterate until you meet the Null Character
The example code would be like this
char* name = "Some Name";
int len = 0;
while (name[len] != '\0') {
len++;
}
Also, if it is a char pointer, not char array, sizeof(char*) will always return 4 in 32-bit application and return 8 in 64-bit application (the size of the 'pointer' itself - the memory address size)
#include <stdio.h>
int main()
{
int i=0;
char *name = "pritesh";
for(i=0;;i++)
{
if(name[i] == '\0')
{
break;
}
}
printf("%d", i);
return 0;
}
This should work
note: this might be syntactically incorrect as I have not had my hands on c since a long time

Function to reverse a two-dimensional set of strings in C isn't reversing more than the first and last characters

this is my first post in Stack Overflow. If I am missing anything, please let me know and I will try to add more information.
The function below is only supposed to use pointer operations and not array operations, as part of an assignment.
I have this function in C that is part of a larger program:
void reverseString(char strings[NUM_STRINGS][STRING_LENGTH])
{
int i, j;
char *ptr; //Declare pointer variable.
for (i = 0; i < NUM_STRINGS; i++)
{
ptr = strings[i];
do { //Here, we ignore the null terminators in the char array.
ptr++;
} while (*ptr != '\0');
ptr--; //Iterate the pointer variable once downward.
j = i;
while (strings[j] < ptr) //While loop for reversing the string
{
//printf("ptr: %d\n", ptr);
//printf("strings[j]: %d\n", strings[j]);
char temp = *strings[j];
*strings[j++] = *ptr;
*ptr-- = temp;
}
}
}
What it is supposed to do is accept a 2D char array with 4 strings and with each string holding up to 32 bytes of text. Then, it reverses each string in-place in the array. For example, if I input the four strings:
Hello
World
Good
morning
It is supposed to then return:
olleH
dlroW
dooG
gninrom
However, what ends up happening is that only the first and last characters of each string are reversed. For example:
oellH
dorlW
dooG
gorninm
I have tried different solutions such as using i instead of j in the while loop or using prefix ++ instead of suffix, but nothing has worked yet. Any pointers as to what I should be looking for?
Thank you.
The solution is below. As described in my comment below, I added a secondary pointer instead of using strings[j] in the loop. The pointer now references to the beginning of the string instead of the entire array of strings.
void reverseString(char strings[NUM_STRINGS][STRING_LENGTH])
{
int i, j;
char *ptr; //Declare pointer variable.
char *ptr2;
for (i = 0; i < NUM_STRINGS; i++)
{
ptr = strings[i];
ptr2 = strings[i];
do { //Here, we ignore the null terminators in the char array.
ptr++;
} while (*ptr != '\0');
ptr--; //Iterate the pointer variable once downward.
j = i;
while (ptr2 < ptr) //While loop for reversing the string
{
char temp = *ptr2;
*ptr2++ = *ptr;
*ptr-- = temp;
}
}
}

How can I search through an array that returns both the position of the value and the number of comparisons?

I have a function that searches an array for a given value and returns its position if found. However, I also want it to update the number of comparisons it took to search through the entire array. But it is not working and crashes once it exits the function and calls for the parameter.
int linSearch(int arr[], int size, int target, int* numComparisons) {
int i;
int count = 0;
for (i = 0; i < size; i++) {
count++;
if (arr[i] == target) {
numComparisons = count;
return i;
}
}
return -999;
}
I am calling the function with this
linSearch(userArray, userEntries, valSearch, *numLinSearch)
and the variable numLinSearch is this
int *numLinSearch = 0;
When i try to print out something like printf("%d", numLinSearch); the program crashes. How do I fix this?
numComparisons = count;
You are changing the value of the pointer, not value of the pointed object. It should be rather:
*numComparisons = count;
numComparisons has to contain the address of a variable so that the function can process its data. Therefore you should call linSearch like this:
int numComparisons = 0; /* for example */
linSearch(userArray, userEntries, valSearch, &numLinSearch)
rather than:
int *numComparisons = 0; /* numComparisons is a null pointer */
It crashes not when you call printf, but when you call linSearch.
The correct call should look like this:
linSearch(userArray, userEntries, valSearch, &numLinSearch);
to pass numLinSearch by reference
When you initialize
int * numLinSearch = 0
you set numLinSearch to NULL and when you attempt to dereference it in the method it crashes
initialize it as
int * numLinSearch = malloc(sizeof(int));
or alternatively, (not recommended if you want to save this pointer out of scope)
int temp = 0;
int * numLinSearch = &temp;

Passing entire array to the function in C

I have written a program for insertion shot like following:
int _tmain(int argc, _TCHAR* argv[])
{
int arr[10] = {1,2,3,10,5,9,6,8,7,4};
int value;
cin >> value ;
int *ptr;
ptr = insertionshot(arr); //here Im passing whole array
BinarySearch(arr,value);
return 0;
}
int * insertionshot(int arr[])
{
//Changed after a hint (now, its fine)
int ar[10];
for(int i =0;i < 10; i++)
{
ar[i] = arr[i];
}
//Changed after a hint
int arrlength = sizeof(ar)/sizeof(ar[0]); //here array length is 1, it should be 10
for(int a = 1; a <= arrlength -1 ;a++)
{
int b = a;
while(b > 0 && ar[b] < ar[b-1])
{
int temp;
temp = ar[b-1];
ar[b-1] = ar[b];
ar[b] = temp;
b--;
}
}
return ar;
}
The problem is after passing the whole array to the function, my function definition only shows 1 element in array and also "arraylength" is giving 1.
int arr[] in a function formal parameter list is a syntax quirk, it is actually processed as int *arr. So the sizeof trick doesn't behave as you expect.
In C it is not possible to pass arrays by value; and furthermore, at runtime an array does not remember its length.
You could include the length information by passing a pointer to the whole array at compile time:
int * insertionshot(int (*arr)[10])
Of course, with this approach you can only ever pass an array of length 10. So if you intend to be able to pass arrays of differing length, you have to pass the length as another parameter.

How to set a pointer to struct to NULL in C?

I have an array of pointer to struct, and for any reasons when I print this array, there is a spare element at the end of it, and thus causes the code to print a NULL byte at the end.
Is there anyway I can delete the last chunk of memory?
For example:
typedef struct
{
char *name;
} B;
typedef struct
{
B *var;
} A;
int main() {
int num = 5; //for example
A *foo = malloc(sizeof(A));
B *bar = malloc(num * sizeof(B));
for (int i = 0; i < num; i++) {
bar[i] = *create_b(&bar[i]); // some function that works.
}
foo->var = bar;
while (foo->var != NULL) {
printf("This is %s\n",foo->var->name);
foo->var++;
}
}
Everything is printed out just fine, but there's an unwanted printing at the end of the loop. Something like:
This is A
This is B
This is C
This is D
This is F
This is
Apparently the array only has 5 elements, the last one prints nothing.
Your printing loop is:
foo->var = bar;
while (foo->var != NULL) {
printf("This is %s\n",foo->var->name);
foo->var++;
}
But foo->var will never equal NULL, since you're just incrementing a pointer, so you will eventually read past the end of the bar array and your application will probably crash.
If you replace the while loop with for (int i = 0; i < num; i++), it will print the correct number of elements.
You can't do foo->var++, because there is no place in the array that is set to NULL. Also, using that ++ changes foo->var so after the loop foo->var no longer points at the start of the array, and you can not access the array again.
You need to allocate memory for some end-of-array marker, just like strings has the character \0 to mark the end of the string.
Try the following:
int main() {
int num = 5; //for example
A *foo = malloc(sizeof(A));
B *bar = malloc((num + 1) * sizeof(B)); // +1 for array terminator
for (int i = 0; i < num; i++) {
bar[i] = *create_b(&bar[i]); // some function that works.
}
bar[i].name = NULL; // Use this as a marker to mean end of array
foo->var = bar;
for (B *tmp = foo->var; tmp->name != NULL; tmp++) {
printf("This is %s\n",tmp->name);
}
}
Edit Had some errors in the code.
Your problem is probably in the function create_b, which you did not post.
Edit: no, that's probably wrong, sorry.
But surely this isn't what you want:
bar[i] = *create_b(&bar[i]);
You both pass in the address of bar[i] and set it equal to whatever the return value points to?

Resources