0.o please assist, seemingly impossible program!

Dec 29, 2013 at 7:17pm
Hello everyone:), i need help with the following:

I need to make a program that takes an input from file(.txt) with this format!

1
2
3
4
5
e 1234
d 0189
d 1234
e 123456
e 9999


the input length is undefined, the "e" means encrypt and the numbers preceding the letters are a "code" that needs to be either decrypted or encrpyted.

What i did:
input is from a text file, so since it has undefined length, i put all the .txt content into a vector, and successfully separated the .txt content into alphabets and numbers as follows into their respective string vectors:

1
2
3
4
5
6
alphabet vector : num vector
e               :  1234
d               :  0189
d               :  1234
e               :  123456
e               :  9999


my code at present!

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
//bloody problem giving me headache 0.o

#include <iostream>
#include <fstream>
#include <cstdlib>
#include <vector>
#include <cstring>
#include <string>
using namespace std;

int main()
{
    vector<string> data, alpha;
    vector<int> num;
    int cntr = 0;
    string info = "";

    ifstream infile("input.txt");

    while(infile>>info) {
        data.push_back(info);
        cntr++;
    }

    //store numbers alone into specific vector
    for(int i = 1; i<cntr; i+=2)
         num.push_back(atoi(data[i].c_str()));

    //store alphabets alone into specific vector
    for(int j = 0; j<cntr; j+=2)
        alpha.push_back(data[j]);
}



edit :

Since i have a vector with the string "1234" , i used atoi to convert that string to a number i.e becomes 1234(one thousand two hundred and thirty four), what i need to do now is manipulate each number in 1234 , it is required that i add a 7(seven) into each individual number that makes up 1234 and then take the mod of each number with right after adding the 7 to it!, i hope this makes sense,~ English is not really my strong point

i,e need to breakdown 1234 into 1,2,3,4 and then perform the operation explained earlier!
Last edited on Dec 31, 2013 at 10:33am
Dec 29, 2013 at 7:24pm
Why exactly are you having problems with atoi?

Personally I would make "num" an int vector then do something like this.
1
2
for(int i = 1; i<cntr; i+=2)
        num.push_back(atoi(data[i].c_str()));  //atoi takes a C style string so .c_str() is needed 
Dec 29, 2013 at 7:24pm
One way would be to convert the strings to numbers:
http://www.cplusplus.com/articles/D9j2Nwbp/

But why not save some trouble and just read them from the file as integers?
1
2
3
4
char eOrD;
int number;
while (infile >> eOrD >> number) {
    // etc. 

The >> operator for streams will automatically gobble up any leading whitespace characters, so you won't have to worry about "accidentally" reading in a space or newline character or anything like that.
Dec 30, 2013 at 5:14pm
firstly thanks for the reply to all!, thanks for the convenient method to long double main and for the atoi usage to James2250,

i have yet another problem, since i am reading in the number as a string i.e 1234, when i convert it to an int atoi takes it as one number such that i cant access the individual number in "1234" that is i can only chose "1", or "2" in 1234 such that i can change them , please help me with a way around this THANKS! :)
Dec 30, 2013 at 8:20pm
This will vary depending on the digit you wish to access and how you wish to encrypt, but assuming you've converted to int and you wish to change the 2:
1
2
3
4
int num; //will be 1234 for example
int remainder = num % 100; //remainder equals 34
num = num - (num % 1000); //num now equals 1000
num += 900 + remainder; //num now equals 1934 


You could make the method much more generalized by first figuring out how many digits are in the number (keep taking num /= 10 until there's nothing left, you'll probably want a copy of num) then taking a random position in the number and modifying it in some way.
Dec 30, 2013 at 8:44pm
i need to operate on the numbers as though they were integers
I think from other comments, you mean you want to operate on the individual digits as though they were numbers.

If that's the case, it might be better to keep the input as a string, that makes it easy to access each individual character. In order to convert a character such as '7' into the number 7, there are several possible solutions. One is something like this:
1
2
char ch = '7';
int num = ch - '0';

and to convert back again, you might do:
 
ch = num + '0'; // assuming num is in range 0 to 9. 
Dec 31, 2013 at 2:20am
edit : ...

So for 1234 you want to do this?
1234
(1+7)(2+7)(3+7)(4+7) = (8)(9)(10)(11)
(8%10)(9%10)(10%10)(11%10) = 8901 //final number

If so you can use a loop something like this:
1
2
3
4
5
6
7
8
9
10
//intNum is a vector with integer elements 1, 2, 3, and 4
int size = intNum.size();
int index, curNum;
for (index = 0; index < size; ++index)
{
   curNum = intNum[index];
   curNum += 7;
   curNum %= 10;
   intNum[index] = curNum;
}

To create intNum, you can use num as defined in your code and atoi() for every index of num.
Dec 31, 2013 at 6:59am
thannks for the reply heebleworp, so how did you break down the number 1234 into 1,2,3,4 is the method you described earlier the only way?
Last edited on Dec 31, 2013 at 7:02am
Dec 31, 2013 at 9:51am
is the method you described earlier the only way?

I already showed an alternative way. Though I assumed you already knew how to access the individual characters of a string.
1
2
3
4
5
string s = "4635";
for (unsigned int i=0; i<s.size(); i++)
{
    char ch = s[i]; // get individual character of string.
}
Last edited on Dec 31, 2013 at 10:02am
Dec 31, 2013 at 10:41am
@ chervil.. please have a look at my code, i am using a vector of strings.., i dont have a mere string like s = "4635" but have num[0] = "1234", hence i dont see how i can implement what you suggested i.e
ch = s[i]
since this will simply give me elements of the string vector! in my case unlike in the general case of s = "4635" 0.o and not elements of the string within the vector,, I really dont know how to explain this :( could you please run the code maybe?

Thanks for the patience, really apreciate it!
Last edited on Dec 31, 2013 at 10:42am
Dec 31, 2013 at 11:49am
@Ozwurld I see that in your code you've used atoi() to convert the string to an integer. But the next thing you want to do is to split the integer into individual digits. My suggestion was only an opinion, that it might be better to keep the value as a string throughout, as this makes it (again in my opinion) easier to access each digit.

Since you will have a vector of strings, then num[i] would be a string, you could access each character like this: num[i][j] but it might be clearer to introduce a temporary variable string s in the example below, and use that for the required operations. I've based my code on your original code, but simplified it a little, notice I have only two vectors and the variable cntr is not needed because the vector maintains its own count of the number of elements.

My apologies for this distraction as you are receiving several different sets of advice, and so I may be adding to the confusion. Anyway, I hope it helps a little.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
#include <iostream>
#include <fstream>
#include <vector>
#include <string>

using namespace std;

int main()
{
    vector<string> alpha;
    vector<string> num;

    string info, number;

    ifstream infile("input.txt");

    while(infile>>info>>number)
    {
        alpha.push_back(info);
        num.push_back(number);
    }

    for (unsigned int i=0; i<num.size(); i++)
    {
        string s = num[i];
        for (unsigned int j=0; j<s.size(); j++)
        {
            char ch = s[j];
            cout << ch << " ";
        }
        cout << endl;
    }
}

Output:
1 2 3 4
0 1 8 9
1 2 3 4
1 2 3 4 5 6
9 9 9 9


or replace the code at line 26 with this:
26
27
28
29
30
        for (unsigned int j=0; j<s.size(); j++)
        {
            int n = s[j] - '0';
            cout << n << " ";
        }

The output looks just the same, but this time using int instead of char.
Last edited on Dec 31, 2013 at 2:45pm
Dec 31, 2013 at 12:32pm
Well there is another way but it may seem a bit long. Using C++11 to make coding life easier:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
//Note: This code requires a compiler that supports C++11
#include <iostream>
#include <string>
#include <vector>
#include <algorithm>

using namespace std;

int processNum(string s) //This function does the stuff you said (add 7 then mod and stuff)
{
    vector<int> numbers;
    int num = stoi(s); //Using stoi convert the string to an integer
    for(int i = 0; i<s.length(); i++)
    {
        numbers.push_back(((num%10)+7)%10); //Slice the number from end and add 7 then take mod 10
        num = num/10; //Reduce the number by 1 digit from the end
    }
    reverse(numbers.begin(), numbers.end()); //Reverse the vector
    string r = ""; //Initialize an empty string to store the result
    for(int j = 0; j<s.length(); j++)
    {
        r = r+to_string(numbers[j]); //Convert each int in the vector to string and concatenate it to r
    }
    return stoi(r); //Convert r to int and return the result
}

int main()
{
    //The lines below must be self explanatory
    string the_input = "4325";
    int result = processNum(the_input);
    cout << result << endl;
}
Last edited on Dec 31, 2013 at 1:36pm
Dec 31, 2013 at 5:50pm
As much as I like Stormboy's code I think you're going to have to use Chervil's method or something similar due to input with leading zeros:
d 0189
"0189" gets converted to 189 on line 12, so the leading zero is neglected. The same issue can also pop up on line 24. You could explicitly check for leading zeros but it is simpler imo to use Chervil's method. Unless you want to get rid of leading zeros, in which case Stormboy's method is easier.
Jan 5, 2014 at 10:12am
Thanks for the help guys, and for being patient with me,, i really appreciate this a lot:)
Topic archived. No new replies allowed.