How to save a string into dynamic char array - c++

The array should be dynamic, but it is fixed.
Printing the array gives nothing.
I'm trying to create a dynamic char array, get a string line from user, save line string char by char into the array.
#include <iostream>
#include <string>
using namespace std;
int main()
{
char* lenptr = NULL; // declare a pointer initialized with null
int leng, arrsz;
string mystr;
cout << "enter a string: ";
getline(cin, mystr); // input a line of string
leng = mystr.length(); // get length of string
cout << "string length: " << leng << endl;
lenptr = new char[leng+1]; // declare a dynamic char array with length+1
for (int i = 0; i < leng; i++)
{
lenptr[i]=mystr[i]; // fill array with saved string
}
lenptr[leng] = '\0'; // save '\0' in last array cell
arrsz = sizeof(lenptr); // get size of array
cout << "size of array after saving " << leng << " chars: " << arrsz << endl;
cout << "string in array: ";
for (int j = 0; j < leng; j++) // print array
{
lenptr[j];
}
cout << endl;
// delete pointer
delete[] lenptr;
lenptr = NULL;
system("pause"); // pause system
return 0;
}
enter a string: helloworld
string length: 10
size of array after saving 10 chars: 8
string in array:
Press any key to continue . . .

You can't get the size of an array allocated with new[]. Although std::string is the recommended way to go about this, a vector would've been a more viable choice if the string absolutely had to be stored in a data structure.
At any rate, your program wasn't printing the characters of the array because you forgot a std::cout in the for loop:
for (int j = 0; j < leng; j++) // print array
{
cout<<lenptr[j];
}
and to actually print out the size of the array just use the leng variable you defined earlier:
cout << "size of array after saving " << leng << " chars: " << leng + 1 << endl;

Related

input string as character array in c++

I have search a lot but i haven't find my answer
I want to write a program that will give an array with 3 members
and then i want to print array with 3 members :
char array[3] ;
for(int i=0;i<3;i++){
cin>>array[i] ;}
But the point is , i don't want to cin array members in character ,and i want this in string ;
but the another point is i don't want to use #include <string.h>
what i have to do ?
I want to give input array from user in this form:
char array[3]={"input1","input2","input3"}
for(int i=0;i<3;i++){
cin>>array[i] ;
}
cout<<array[0]<<" "<<array[1]<<" "<<array[2] ;
//output = input1 input2 input3
char array[3][10];
for (int i = 0; i < 3; i++) {
cin >> array[i];
cout << array[i] << endl;
}
Where the 2nd size of the array depends on the length of the input string.
char array[n] will only store n characters; use char array[n][m]. Remember, a c string (char[]) is different than string. In your case, you would want `char array[3][length]' where length is the max space to 'reserve' for each word.
char array[3][32]; //you wont need to fill this with data right away
for (int i = 0; i < 3; i++)
{
std::cin >> array[i];
}
std::cout << " " << array[0] << " " << array[1] << " " << array[2];
Hope This Solves!
#include <iostream>
using namespace std;
int main()
{
char arr[3][100]; // Declaring the two dimensional character array 3 denotes number of inputs whereas 100 dentoes the length.
for(int i=0;i<3;i++){
cin>>arr[i];
}
for(int j=0;j<3;j++){
cout<<arr[i]<<" ";
}
return 0;
}

How To Print Values Stored in an Array

I am working to create a function where I take in 6 values (3 strings, 3 ints), store those values in arrays, then print out each of those values in pairs of 2
Here is what I have:
#include <iostream>
#include <string>
using namespace std;
int main()
{
const int SIZE = 3;
int time[SIZE] = {};
string name[SIZE] = {};
for (int a = 0; a < 3; a++)
{
cout << "Enter runner name: ";
getline (cin, name[+1]);
cout << "Enter runner time: ";
cin >> time[+1];
cin.ignore();
}
for (int a = 0; a < 3; a++)
{
cout << name << " finished in " << time << "\n";
}
return 0;
}
I would like my output to look like this:
name1 finished in time1
name2 finished in time2
name3 finished in time3
Currently, my output looks like this:
0x22fdf0 finished in 0x22fe10
0x22fdf0 finished in 0x22fe10
0x22fdf0 finished in 0x22fe10
How can I get the inputs to be stored in the arrays then output those values to the user?
If this has been answered already, apologies. I haven't been able to find an example where the arrays are populated with user input values and then returned to the display.
You need to actually index the array using the [] subscript operator. Likewise, when printing, you should attempt to index an element in the array. Since when you attempt to print the array itself, the compiler will implicitly convert the array to a pointer, which, when printed, will print the memory address of the first element in that array, rather than the element itself.
So you could dereference the arrays to get the first value in each, but a better way is to index it by the a variable in your for loop, like so:
#include <iostream>
#include <string>
using namespace std;
int main() {
const int SIZE = 3;
int time[SIZE] = {};
string name[SIZE] = {};
for (int a = 0; a < 3; a++) {
cout << "Enter runner name: ";
getline(cin, name[a]);
cout << "Enter runner time: ";
cin >> time[a];
cin.ignore();
}
for (int a = 0; a < 3; a++) {
cout << name[a] << " finished in " << time[a] << "\n";
}
return 0;
}
Alternatively, if you wanted to not index it, you could use your original approach, but then you would have to dereference the pointer using the * dereference operator:
for (int a = 0; a < 3; a++) {
cout << *name << " finished in " << *time<< "\n";
}
However, now you would simply print the first element three times. So to remedy this, you need to employ some pointer arithmetic, and increase the value by a, to get the elements, 0, 1, and 2 past the first element respectively:
for (int a = 0; a < 3; a++) {
cout << *(name + a) << " finished in " << *(time + a)<< "\n";
}
So some things to look up:
* Dereferncing
* Subscripting
* Implicit array to pointer conversion

How do I change the size of an array and fill it with automated elements?

I have an array with set elements 1 - 10. I have decided the size of the array and I have decided the elements of the array. My question is, how do I create an array of size x and fill it with elements 1,2,3,4 . . .
//sets values of the array elements and print them.
cout << "Array should contain x integers set to 1,2,3" << endl;
// QUESTION: How can I change the size of the array and have
// have values automatically entered?
int array[] = { 1,2,3,4,5,6,7,8,9,10 };
for (int i = 0; i <= (sizeof(array) / sizeof(int)-1); ++i) {
// sizeof(array)/sizeof(int) = 36/4. ints are 4.
cout << "Element " << i << " = " << array[i] << endl;
}
cout << "The number of elements in the array is: "
<< sizeof(array) / sizeof(int) << endl;
cout << endl;
cout << endl;
you can use dynamic memory allocation approach for your array, there you can give as much size as you want. Thanks.
//Variable size of Array program to print Array elements
#include <iostream>
using namespace std;
int main()
{
cout << "Enter Array size x:" << endl;
int x = 0;
cin >> x;
int *ptrArray = new int[x];
//Inittialise Array
for (int i = 0; i < x; i++)
{
ptrArray[i] = i + 1;
}
//Print Array elemts
cout << "Array elements:";
for (int i = 0; i < x; i++)
{
cout << ptrArray[i] << endl;
}
delete[] ptrArray;
return 0;
}

An error when dynamically allocating memory for a char*

So the main problem is there is run time error in the code:
char *wordBank[]= {new char[numWords+1]};
char buffer1[41];
for(int i=0; i<numWords;i++){
ifile >> buffer1;
int len = strlen(buffer1);
cout << buffer1<<"and"<<len <<endl;
wordBank[i] = new char[len + 1];
strncpy(wordBank[i], buffer1,len);
cout << wordBank[i]<<"and"<<len <<endl;
}
is it starts to mess up with what is in wordBank. It gets the words from a txt file into buffer1 and then copy if into the dynamically allocated char* array of wordBank. However I always get segmentation fault and the words are all incorrect. What did I do wrong?
You can simplify the code using C++ instead of C:
vector<string> wordBank(numWords);
string buffer1;
for (int i = 0; i < numWords; i++) {
ifile >> buffer1;
size_t len = buffer1.length();
cout << buffer1 << "and" << len << endl;
wordBank[i] = buffer1;
cout << wordBank[i] << "and" << len << endl;
}
Or even simpler, but adding error checking:
vector<string> wordBank(numWords);
for (int i = 0; i < numWords; i++) {
if (ifile >> wordBank[i])
cout << wordBank[i] << "and" << len << endl;
else { // no more words
wordBank.resize(i); // chop off the unused portion
break;
}
}
This line is wrong:
char *wordBank[] = {new char[numWords+1]};
wordBank is an array with one element, the value of that one element is a pointer to a character array with numWords+1 characters. When you access wordBank[1] you're outside the bounds of the array, which results in undefined behavior.
What you apparently want is:
char **wordBank = new char*[numWords];
This creates a dynamically-allocated array of numWords char* elements, which you will then assign in the for loop.
I don't see any need for numWords+1.

null terminated char array (c-string) not printing without for loop

**I can't use vectors, or any functions from the standard library with this program. Hence why I am writing it all myself.
Alright, this program is just about finished. All my user defined functions are working fine, except for the reverseCString function. When I run the program, and enter a string of "hello", I can select menu option "rev" to reverse the string. My main function then calls the reverseCString function, and uses the for loop in my main to print out my reversed c-string. The program works fine at this point, until the do-while loop continues..
After the rv function is called though, the program loops to continue to allow the user to modify their string, as it should. However, my c-string vanishes at this point. I can still operate on it if I use the other commands/funtions, but the c-string doesn't print to cout.
I don't understnad what is causing this, but I have isolated the problem down to the reverseCString function.
Here is my code so far:
#include<iostream>
#include<stdlib.h>
#include<cstring>
#include<string>
#include<math.h>
using namespace std;
void shiftLeft(char szString[], size_t shiftBy)
{
const char *p = szString;//
while (*p) ++p;//advance p to point to the the null terminator, found via personal research at http://stackoverflow.com/questions/12201815/what-difference-between-whilepp-while-p-and-whilep
size_t len = p - szString;//len is set to the size of our c-string
if (len > 1 && (shiftBy %= len))
{
char *ends[] = { szString+shiftBy, szString+len, szString+(len - shiftBy) };//create a temporary array for storage
for (size_t i = 0; i < 3; ++i)//use a for loop to flip the first three character
{
char *start = szString, *end = ends[i];
while (start < --end)//now flip the rest of the characters
{
char ch = *start;
*start++ = *end;
*end = ch;
}
}
}
}
void shiftRight (char szString[], int size, int shiftBy)
{
if(shiftBy > size){
shiftBy = shiftBy - size;
}
if(size == 1){
//do nothing, exit function with no change made to myarray
}
else{
char temp;
//for loop to print the array with indexes moved up (to the right) --> by 2
for (int i=0; i < size; i++)
{//EXAMPLE shift by 3 for a c-string of 5
temp = szString[size-shiftBy];//temp = myarray[2]
szString[size-shiftBy] = szString[i];//myarray[2] = myarray[i]
szString[i] = temp;//myarray[i] = temp(value previously at index 2)
}
}
}
void reverseCString(char szString[], const size_t& size){
char temp;
int i = 0;
int j = size-1;
//we can use a simple tep variable to flip everything
while(i < j)
{
temp = szString[i];
szString[i] = szString[j];
szString[j] = temp;
i++;
j--;
}
}
int main(){
string repeat = "";
string userInputString;
cout << "Please eneter your string: " << endl;
//cin >> ws;
getline(cin,userInputString);
char * szString = new char [userInputString.length()+1];
strcpy (szString, userInputString.c_str());
do {
cout << "Your c-string is: " << szString << endl;
string commandString = "";
cout << "Please enter a command: ";
getline(cin,commandString);
if (commandString[0] == 'L'){
cout << "You have chosen to shift your string left by " << commandString[1] << " characters." << endl;
const char * shiftLeftPtr = &commandString[1];
//convert this value to an int for our function
int shiftLeftBy = atoi(shiftLeftPtr);
//run our shifleft function
shiftLeft(szString,shiftLeftBy);
//print the results
cout << "Your c-string, shifted left by " << commandString[1] << endl;
cout << szString;
}
if (commandString[0] == 'R'){
cout << "You have chosen to shift your string right by " << commandString[1] << " characters." << endl;
const char * shiftRightPtr = &commandString[1];
//convert this value to an int for our function
int shiftRightBy = atoi(shiftRightPtr);
//run our shiftright function
shiftRight(szString,userInputString.length(),shiftRightBy);
//print the results
cout << "Your c-string, shifted right by " << commandString[1] << endl;
cout << szString;
}
if (commandString.compare("rev") == 0){
cout << "You have chosen to reverse your string. " << endl;
//run our reverseArray function
reverseCString(szString,userInputString.length()+1);
cout << "Your c-string, reversed: ";
for(int i = 0; i < userInputString.length()+1; i++){
///////////////////////////right her seems to be my issue
cout << szString[i];
}
}
if (!(commandString[0] == 'R' || commandString[0] == 'L' || commandString.compare("rev") == 0)){
cout << "You have entered an invalid selection." << endl;
}
cout << "\nEnter 'quit' to close the program, anything else to continue: ";
getline(cin,repeat);
}while(repeat.compare("quit") != 0);
return 0;
}
Your length logic is broken. Say the string contains "bar\0". You do this:
reverseCString(szString,userInputString.length()+1);
Now, length is 3, and you pass 4 to reverseCString. Then this happens:
void reverseCString(char szString[], const size_t& size){
char temp;
int i = 0;
int j = size-1;
Now, i is 0 and j is 3. So you swap items 0 and 3. Well, what are the items?
0 = b
1 = a
2 = r
3 = \0
When you swap items 0 and 3, you create a string that starts with a terminator, "\0rab". Of course printing that out won't produce anything.