Link to home
Start Free TrialLog in
Avatar of underscore_elite
underscore_elite

asked on

Stripping the spaces from a sentence.

Hello all again, back with another noob project and my teacher once again acts like it is a test and says "read the book" if you have questions. He might as well not be a teacher.

Well, my lab is as follows:

"Using pointers create a function called stripWhite that will strip all of the white spaces from an array of characters. Your function should return the number of white spaces that you deleted.
White spaces can be a number of characters, but in our case we are only concerned with the blank space character (space bar) which is the character Decimal 32 or Hex 20.

Your prototype should be something like:

int stripWhite(char *str);  << This should be used for the function that will strip the spaces.

Your output should look something like the following:

      Enter a sentence and I will strip out all spaces:
      The quick brown fox jumped over the lazy old dog
      Your sentence without spaces is:
      Thequickbrownfoxjumpedoverthelazyolddog.

Note: Passing an array does not count as using pointers. So, if your only use of pointers is this:
int stripWhite(char *str)
{

}
Think again!"

Below is my logic behind the problem, I know it is not in code, but it is simply the logic, the "way to solve" the issue. I am just learning so I need to take this step by step and hopefully you guys will be there to help me out!

One main concern that I have is the last note... It states that using pointers just to point to the array in the header of the function is NOT using pointers to pass the array????? I have no idea what this means and once again, he does not answer emails so please help me out!

As you can see from my logic below, I am very amateur at this, also, I have no idea how to re-print the sentence without spaces. I have a good idea of how to count the no. of spaces, but not how to re-print the sentence without spaces.

I can only use really basic libs like iostream, ctime, and cmath.
I can only use cin and cout.

Thanks in advance for reading, hopefully I can get some answers to my preliminary questions. I will go ahead and start writing code and post up what I come up with soon! Thanks again.
int main()
{
 
Declare the character array.
 
Program asks for sentence.
 
The input breaks the sentence into words and spaces, putting each word or space into it's own array location.
 
Call stripWhite function (not sure what to use for arguments since it will be using pointers)
 
Retrieve the return value from the stripWhite function.
 
Print out the number of spaces.
 
Print out the sentence without the spaces
 
Return 0;
}
 
int stripWhite(char *array)
{
 
Use a for loop to go through each block of the array and using an if statement to add to a counting integer to count the amount of times the array section equals a white space.
 
Return the no. of spaces.
}

Open in new window

Avatar of RishadanPort
RishadanPort

Basically the teacher does not want you to use array syntax using "[]" notion, but instead using only pointer syntax, with "*".... Personally... There really isn't much of a difference, but that is what the teacher says.

Example of 2 ways with using "[]" syntax (the way the teacher does not want it) and with "*" syntax

1. char[] someString = {'a', 'b', 'c', 'd', 'e', 'f'};
someString[5] = 'g';

2. char * someString = "hello";
char * charPtr = someString + 2;
*charPtr = 'o';
Avatar of underscore_elite

ASKER

Thanks Rishadan for responding, you make sense, but this makes me erase the array that I just built lol! >.<

I am a bit confused because in my class, during the lecture, my teacher simply said that a pointer (using the *) is simply just pointing to something else. So in your sample code, every variable that you created (someString, and charPtr) have the * in them already, so if everything is a pointer, what is it pointing to?

char * someString = "hello";  // Are you declaring a NEW string called someString here? Or did it already exist? 'hello' is being placed into the whole string?

char * charPtr = someString + 2;  // This is placing whatever value is in someString + 2 into the character variable charPtr?

*charPtr = 'o'; // After declaring charPtr as being someString +2, why would you then set it to zero?

Yes, I am sure I look like an idiot asking these stupid questions, but I am truly looking to learn this language so I want to ask as many questions as possible and learn it as much as possible....


(still writing code btw so I will post what I have done so far in a few...)




"Below is my logic behind the problem, I know it is not in code, but it is simply the logic, the "way to solve" the issue. I am just learning so I need to take this step by step and hopefully you guys will be there to help me out!"

-->This is always the approach you should do, and that is a good thing you are putting it into logic first.


I just want to warn you ahead of time, that using char pointer (char *) is not entirely the same as using other pointers like int *, double * ...

char * and a string are basically the same thing.

What char * is doing, is it is "pointing" to the memory location of the first character. It, itself, does not store the entire string.

What happens when you allocate a char *, is that it inserts a null character ('\0') at the end of the string...

so for example if you allocated this:

char * var = "hello";

what is actually happening is that

"hello\0" has been allocated in memory where "\0" is the null character, and var is pointing the the first character h
If this null character, is some how removed.... Then there can be major problems. What it will do, is that it will continue to print each byte after your allocated character until it finds a null character.

So, for example if we do this:

char * var = "hello";
var[5] = 'o';    <---------- Ooops we went out of bounds... ontop of the null character

this can cause problems... Try running a few tests and muck around with char * before starting your application... Try this for example. See what happens
ASKER CERTIFIED SOLUTION
Avatar of RishadanPort
RishadanPort

Link to home
membership
This solution is only available to members.
To access this solution, you must be a member of Experts Exchange.
Start Free Trial
You are literally making a lot of stuff clear, you really need know know how grateful I am that you are sharing your knowledge with me.

I am experimenting with stuff like...

char *var = "hello all I am learning Cplusplus";
cout << var[2] << " " << var[5] << endl;

and how that will print out the letters in the certain locations in the string. Cool stuff!

That clears up a lot. However I am stumped in thinking... okay how can I create a string (like var above) that will dynamically enter the values? So instead of having "hello all I am learning Cplusplus" it would have to be a character variable there so that the user inputted sentence can be stored in the var string.


Try doing this, and see what it outputs:

char *var = "hello all I am learning Cplusplus";
char *innerPointer = var + 4;

cout << innerPointer << endl;

If I did the syntax properly it should output this:
"o  all I am learning Cplusplus"

What you need to understand is that innerPoint is NOT storing all those characters, it is only holding a memory address that is 4 away from the memory location of var.  Then it prints every character FROM THAT STARTING LOCATION, to null character
If you do this:

var + 0  -- > that refers to pointing to 'h' memory location
var + 1 -- > that refers to pointing to 'e' memory location
var + 2 -- > that refers to pointing to first 'l' memory location
var + 3 -- > that refers to pointing to second 'l' memory location
var + 4 -- > that refers to pointing to 'o' memory location
Ok so here is the algorithm that I would do:

1. Store Char * and get the user to store some characters here. (don't worry yet how we will do that)
2. Remove White spaces in the character array by "copying" adjacent characters to each other
3. Insert a null character, '\0', at the end of the character array, so that spaces at the end are not printed

Please note that step 2, has a lot of sub steps, but this is the big picture of the problem
In this example, I will show some cases, that you will have to worry about, in these examples, I will use "_" to denote white space to make things clearer

char * var = "hello_____there__"     must be translated to --->   "hellothere\0"
char * var = "hello________"           must be translated to --->    "hello\0"
char * var = "_______"                     must be translated to -->     "\0"    <-- empty string
Boy I guess we are going to have to take this slow with me. I totally understand what you mean about the null character being at the end of the string and automatically assigned there.

Here is my guess at the very beginning of the user input area of the program.... It does compile but I get a single debug error after it compiles. Stating var has not been initialized. How do I know how large to initialize var without knowing how large the sentence will be?



int main() 
{
char *var;
 
cout << "Please enter a sentence: " << endl;
cin >> var; // I would think that this would input even a sentence just the same as it would enter any character(s)
cout << var << endl; // Shouldn't this automatically print whatever was inputted for var?
 
return 0;
}

Open in new window

Noting to my above code... I HAVE to somehow declare how large the string is in the first place if the user is going to enter the values for the character var. For example, I would have to create an array and set it to something like 100 characters and then set var = var[100] and then use CIN to input to the string, causing each character to be in a new location in the array/string. That is the only way I would know how to do this?
Ok so here is where it gets complicated.

Declaring char * like this:

char * var;

is Totally not the same as declaring it like this:

char * var = "hello"


In the second case the compiler does 2 things:
1. It adds the string "hello\0", to a place in memory
2. initializes var to POINT to the memory location of 'h'
and


Case 1 however, is completely different. Case one you are not declaring the pointer to point anywhere.
It only treats char * var; in this case as just a pointer, and does not know how much space to allocate.


Here is where things get a bit tricky,

In order to dynamically allocate a char * in this concept, you need to do this:

char * var = (char *)malloc(sizeof(char) * <number of chars you want to allocate>);


Now... you must must must... when you are finished using this var, free the memory, like this:

free(var);
int main() 
{
//allocate storage for 100 characters dynamically
char *var = (char *)malloc(sizeof(char) * 100);
 
cout << "Please enter a sentence: " << endl;
//store string into var
cin >> var;
//output var
cout << var << endl;
 
//Free... Don't forget!!! If you don't do this, you may cause memory leaks
free(var);
return 0;
}

Open in new window

Okay I knew that I HAD TO declare a constant size of the string somehow, I just did not have any idea how to do it without making it using [ ] syntax.
now actually... This is C syntax... I just realized that you are doing C++

C++ provides a slightly better syntax doing this:

//allocates memory
char * var = new char[<number of chars you want>]

//frees up memory
delete var;
It seems that when a space is entered (using the spacebar) it will stop taking all values after then spacebar.

So If I type in "The quick brown fox" the program will only take "The" and everything after that is not stored in var because the spacebar seems to cancel the input of the characters. I need ALL characters typed, even the space to be stored into the string var. This way, later I can check all spots in the string to see if they equal a "_"


For the actual stripping of the spaces, I can simply write a counter loop that will count ( var[0], var[1], var[2]. etc...) and see if the character in that space is a space "_" or "  "   using an if statement. Now IF the character IS a "_" then it should add to a tally of how many spaces. If it is not, then it simply progresses to the next location in the string. Is this correct thinking?
ah I know what your talking about. I had that same issue. you need to use a "getline" function, instead of a cin. Go search C++ getline function
I hate to jump around from section to section because you are helping me with this one part of the input.

However, I  just got a burst of code written for the function that will count the white spaces, please check the code and syntax and give comments and suggestions, and please please please tell me what I have done wrong and where I am on the right path, and where I am on the wrong path.



int stripWhite(char *A) // Hoping this is passing the values from the string in main to this new char string "A"
{
 
int k;
int count = 0;
 
for (k = 0; k < MAX CHARACTER SIZE; k++)  // I am still working on what to put into MAX CHARACTER SIZE.
{
	if (A[k] == " ") // not sure how to check if the character is equal to a blank space (decimal 32 or hex 20), I think I would reference the memory location... perhaps (A[k] == 32) ???
	{
		count++;
	}
    else
	{
	count = count;
	}
 
 
}
	Return (count);
}

Open in new window

Defining this: " "  <-- double quotes means your dealing with a string... (a bunch of text)

however, if you are dealing with a single character, use sinlge quote:
' ' <---
Okay I got the input to take a sentence. I read about the getline command and I understand it.


char *input  = new char[100];
cout << "Enter the sentence: " << endl;
cin.getline(input, 100);
cout << input << endl;

Now it will take the whole sentence and the spaces until a carriage return is entered.



Attached is now my current whole code. Making progress for SURE, but even if my current code did compile as I would hope it would, I STILL would not be able to print out the sentence without the spaces, I still need to LITERALLY strip the spaces out of the sentence and return the sentence without the spaces in it so that it can be printed!! I really do not know where to start with that, can anyone help with the logic?



#include <iostream>
using namespace std;
 
int stripWhite(char *A)
 
int main() 
{
char *input  = new char[100];
cout << "Enter the sentence: " << endl;
cin.getline(input, 100);
cout << input << endl;
 
int counter = stripWhite(input);
cout << "There were " << counter << " spaces in the sentence." << endl;
return 0;
}
 
int stripWhite(char *A) // Hoping this is passing the values from the string in main to this new char string "A"
{
 
int k;
int count = 0;
 
for (k = 0; k < MAX CHARACTER SIZE; k++)  // I am still working on what to put into MAX CHARACTER SIZE.
{
        if (A[k] == " ") // not sure how to check if the character is equal to a blank space (decimal 32 or hex 20), I think I would reference the memory location... perhaps (A[k] == 32) ???
			{
					count++;
			}
		else
			{
			count = count;
			}
 
}
        Return (count);
}

Open in new window

Okay I got it to strip the spaces!!!!!

Whoo what a relief!

Attached is the working code that will tell the user how many spaces are in the sentence.

I am still not sure how to print out the sentence without the spaces. There has to be a way to erase the space???? Help!



#include <iostream>
using namespace std;
 
int stripWhite(char *A);
 
int main() 
{
char *input  = new char[100];
cout << "Enter a sentence less than 100 characters, I will strip the spaces from it: " << endl;
cin.getline(input, 100);
cout << "" << endl;
 
int counter = stripWhite(input);
cout << "There were " << counter << " spaces in the sentence." << endl;
cout << " " << endl;
return 0;
}
 
int stripWhite(char *A)
{
 
int k;
int count = 0;
 
for (k = 0; k < 101; k++)
{
        if (A[k] == ' ')
			{
			count++;
			}
		else
			{
			count = count;
			}
 
}
return (count);
}

Open in new window

be careful with this line:
for (k = 0; k < 101; k++)

this should be

for(k = 0; k < 100; k++)      going out of bounds like that will eventually create memory leaks


While you are in that function, you need to strip away the spaces. Think about it for a while. I don't want to actually write your entire assignment ;-)
What I would do, is use just 1 single char * to be handling this... however there are a number of ways to do it...

go ahead and research "strcpy", this may give you another idea
Trust me I have not directly copied any of the code you have given me. All of it was typed by myself. I have learned a lot with your help, and the LAST thing I want here is to cheat my way through this. My point is to LEARN this, not to just "pass" the class. My teacher is a lost cause though so I have to turn to the internet for guidance. (and the tutors are only available when I am at work, perfect!)

I will think about it some more about the strip function and look into strcopy. I will post back here with any findings that I have.

Points will be awarded as soon as I get the whole code done and submitted :-)
So would it be something along the lines???



char B[100];
int i;
int k;
int count = 0;
 
for (k = 0; k < 101; k++)
{
        if (A[k] == ' ')
                        {
                        count++;
                        }
                else
                        {
                        for (i = 0; i < 101; i++)
                        strcpy (A[k],B[i]);
                        count = count;
                        }
 
}


This does not compile, but am I thinking correctly?
I would like to use just the 1 since char like you are talking about, somehow to ERASE the value in the given string location??? I tried replacing the ' ' with '' and it did not work....
strcopy needs <string.h> so I cannot use it.


I understand that I need to copy the character value from the "current" value if the statement is in the "else" meaning there is no space there. The problem is that my string is assigned [100] meaning there are 100 values that will print if it is not a space.

                  if (A[k] == ' ')
                        {
                        count++;
                        }
                  else
                        {
                                cout << A[k];
                        count = count;
                        }

int stripWhite(char *A)
{
int k = 0;
int count = 0;
 
//while(A[k] != '\0')    <- not working, creating an endless loop. How can I make it stop when the value of A[k] = /0?
//	{
		for (k = 0; k < 70; k++)
		{		
				if (A[k] == ' ')
					{
					count++;
					}
				
				else
					{
					cout << A[k];
					count = count;
					}		
		}
		
//	}							
return (count); // returning the amount as described in the instructions.

Open in new window

Avatar of Infinity08
I would like to make two remarks :

1) It was suggested earlier (several times) to do something like this :

>> char * someString = "hello";
>> char * charPtr = someString + 2;
>> *charPtr = 'o';

This is not safe, and should not be done !!! "hello" is a string literal, and is often stored in read-only memory. In any case, it should NOT be modified. So, doing this :

        *charPtr = 'o';

where charPtr points inside the string literal is not allowed !!!

If you want to initialize a string with a string literal, then do something like this :

        char charPtr[] = "hello";

which will copy the string literal into the statically allocated array array.
Or this :

        char *charPtr = (char*) calloc(6, sizeof(char));
        strcpy(charPtr, "hello");

which will copy the string literal into the dynamically allocated array array.


2) counting spaces is not the same as stripping spaces. Stripping spaces means removing the spaces from the input.
There is a very simple way to achieve this using pointers : just have a read and a write pointer into the input string. Read a character using the read pointer, and write it to the write pointer only if it's not a space. The string will be modified on the fly, and the result will be the same string without spaces.
Yes infinity. The console would perform illegal operation when performing the task.

I have finished the project according to the instructions and it is submitted. Points have been awarded.

Thanks. I will be posting regarding my next project as this seems to be the most efficient source for help. Thanks again all who contribute.