returning multiple strings from a function - c++

I have a function where i want to be able return what is printed out so then i can print the output on the page. How will i return both of the string which are outputted within both of those if statements ?
std::vector<std::string> el;
split(el,message,boost::is_any_of("\n"));
std::string a ("");
for(int i = 0; i < el.size(); i++)
{
if(el[i].substr(0,3) == ".X/")
{
DCS_LOG_DEBUG("--------------- Validating .X/ ---------------")
std::string str = el[i].substr(3);
std::vector<std::string>st;
split(st,str,boost::is_any_of("/"));
boost::regex const string_matcher(splitMask[0]);
if(boost::regex_match(st[0],string_matcher))
{
a = "Correct Security Instruction";
}
else
{
a = "Incorrect Security Instruction"
}
boost::regex const string_matcher1(splitMask[1]);
if(boost::regex_match(st[1],string_matcher1))
{
a = "Correct Security screening result"
}
else
{
a = "Incorrect Security screening result"
}
return a;
}
}
Thankfull for any help :)

You can return an std::pair of strings, for instance.

Define a class with two appropriately-named string members and return an instance of that.
Then, start to think about what methods or other data would be useful to have on that class.

You can push the strings in a std::vector that is passed to the function as a reference and later iterate over the vector upon return.

I would return a std::pair of bool values (one to indicate if the instruction is correct, and one to indicate if the screening result is correct), and let the calling code interpret the results.

Related

Cannot dereference double pointer, " no match for operator* "

I'm trying to search through an array of pointers to objects of class Shape. I have written the following code. However, I'm getting this error: "no match for operator*", and I don't know where to go from here. Any help is appreciated.
Shape** shapesArray;
bool doesNameExist(string name) {
for (int i = 0; i < shapeCount; i++)
{
if(*(shapesArray[i])->getName() == name)
{
return true;
}
else
{
return false;
}
}
}
shapesArray is a Shape**
shapesArray[i] is Shape*
(shapesArray[i])->getName() is dereferencing shapesArray[i] and calls its
member getName
So far nothing wrong. I guess this is what you actually want to get, but you add another *:
*(shapesArray[i])->getName() tries to dereference what was returned from getName (a std::string perhaps?)
PS: You return from the loop in the first iteration in either case. If you want to search in the array you need to loop until you find it (then return true) or loop till the end (then return false after the loop, because it wasn't found).

How to check if previous return is the current one?

I have the following code:
EDIT
....int l=0
char* FantasiaGameUtils::GetCurrentTask(char *chat_arg)
{ // I know the code looks disgusting but please ignore that as I am only testing now
static char *szTemp1="";
for(int i=0; i<loop; i++)
{
if(task[i][0]!=0)
{
sif (l==0)
{strcpy(chat_arg, task[i]);
}
else
{strcpy(chat_arg, task[i+1]);
}
strcpy(task[i], "");
if (szTemp1!="")
{
MessageBox(0, szTemp1, "szTemp Value", 0);
MessageBox(0, chat_arg, "Initial Value", 0);
return chat_arg != szTemp1 ? chat_arg : NULL;
} else {
l++;
szTemp1 = chat_arg;
MessageBox(0, szTemp1, "szTemp1 Value", 0); // #execute
return chat_arg;
}
}
strcpy(chat_arg, "");
}
return false;
}
EDIT
What I am trying to do is make the return sequence check the previous returned value, and if its not the same as the current one, then return the current value chat_arg, if it is, return NULL.
The purpose of this function is to get the users prompt from the global_chat. An example of a prompt would be !create <game-type> <game-time> <max-players>
This prompt would be individually stored by each word enter (after each space) into the task[][] array, respectively.
From there, this function goes into play. It should copy the current task value (the current word) into the chat_arg variable.
The problem I am experiencing is, for some reason every in my main game loop. The value of chat_arg is kept through-out the game loop. I want to clear this value. I've come up with this method of which I will check if the current value in the function is the same as the previous one and if it is, return NULL (clearing the value), if it's not, then there is no reason to clear the previous value so return the current value.
Might anyone have a better or improved way I can perform this check? Or can anyone PLEASE tell me how I can get the previous returned value from memory and check it against the current value? Thank-you!
1) Add C++ tag to your post, because it is not a pure C code.
for(int i=0; i < loop; i++) // This line will not compile using C compilers.
2) Better return 0 in below line. false does not match to char* you expect.
return false; -> return 0;
My solutions for your problem:
1) Create global variable and your local chat_arg compare to it.
extern char* g_prev_chat_arg = 0;
...
char* FantasiaGameUtils::GetCurrentTask(char *chat_arg)
{
...
//return chat_arg != /*previous return value*/ ? chat_arg : NULL;
if (0 == strcmp(chat_arg, g_prev_chat_arg))
{
return 0;
}
else
{
g_prev_chat_arg = chat_arg;
return chat_arg;
}
...
}
2) Create local static variable within your function char* FantasiaGameUtils::GetCurrentTask(char *chat_arg)and use it like above,
3) Store somewhere in code last returned value from char* FantasiaGameUtils::GetCurrentTask(char *chat_arg) and then pass it each time when you are calling GetCurrentTask(...)
char* FantasiaGameUtils::GetCurrentTask(const char* prev_chat_arg, char* chat_arg)

RapidJSON library getting a value inside an array by its index

{"hi": "hellow",
"first":
{"next":[
{"key":"important_value"}
]
}
}
Accessing RapidJSON inside array:
this works: cout << "HI VALUE:" << variable["hi"].GetString() << endl; this will output: hellow as expected, the problem is to access inside values like if I want to get "Important_Value", I tried something like this: cout << "Key VALUE:" << variable["first"]["next"][0]["key"].GetString() << endl ; but this doesn't work, I want to be able to get the "important_value" by the first item of the array, and in this case it's the [0] that is causing error.
How do I do to get it by its index?
I hope it's clear my explanation.
Thanks in advance.
JSON
{"hi": "hellow", "first": {"next":[{"key":"important_value"} ] } }
Code:
rapidjson::Document document;
if (document.Parse<0>(json).HasParseError() == false)
{
const Value& a = document["first"];
const Value& b = a["next"];
// rapidjson uses SizeType instead of size_t.
for (rapidjson::SizeType i = 0; i < b.Size(); i++)
{
const Value& c = b[i];
printf("%s \n",c["key"].GetString());
}
}
Will print important_value
[Update]
By clever work of contributors, RapidJSON can now disambiguate literal 0 from string. So the issue is no longer happens.
https://github.com/miloyip/rapidjson/issues/167
The problem, as mjean pointed out, the compiler is unable to determine whether it should call the object member accessor or the array element accessor, by literial 0:
GenericValue& operator[](const Ch* name)
GenericValue& operator[](SizeType index)
Using [0u] or [SizeType(0)] can workaround this.
Another way to cope with this problem is stop using overloaded version for operator[]. For example, using operator() for one type of access. Or using normal functions, e.g GetMember(), GetElement(). But I do not have preference on this right now. Other suggestions are welcome.
I noticed this in the tutorial.cpp file;
// Note:
//int x = a[0].GetInt(); // Error: operator[ is ambiguous, as 0 also mean a null pointer of const char* type.
int y = a[SizeType(0)].GetInt(); // Cast to SizeType will work.
int z = a[0u].GetInt(); // This works too.
I didnt test it but you may want to try one of these;
variable["first"]["next"][0u]["key"].GetString()
variable["first"]["next"][SizeType(0)]["key"].GetString()
auto value = my_array[rapidjson::SizeType(index)].GetFoo();
// replace GetFoo with the type of element you are retrieving, e.g. GetString, GetObject
If you want to access it with brackets, then you can use the following:
int i=0;
cout<<"Key VALUE:"<<variable["first"]["next"][i]["key"].GetString()<<endl ;
Output: Key VALUE:important_value
It worked for me.

boost lexical cast <int> check

This should be an easy one. I have a function that traverses a csv and tokenizes based on commas and does things with the tokens. One of these things is convert it into an int. Unfortunately, the first token may not always be an int, so when it is not, I'd like to set it to "5".
Currently:
t_tokenizer::iterator beg = tok.begin();
if(*beg! ) // something to check if it is an int...
{
number =5;
}
else
{
number = boost::lexical_cast<int>( *beg );
}
Seeing as lexical_cast throws on failure...
try {
number = boost::lexical_cast<int>(*beg);
}
catch(boost::bad_lexical_cast&) {
number = 5;
}
I don't normally like to use exceptions this way, but this has worked for me:
try {
number = boost::lexical_cast<int>(*beg);
} catch (boost::bad_lexical_cast) {
number = 5;
}

Evaluating expressions inside C++ strings: "Hi ${user} from ${host}"

I'm looking for a clean C++ way to parse a string containing expressions wrapped in ${} and build a result string from the programmatically evaluated expressions.
Example: "Hi ${user} from ${host}" will be evaluated to "Hi foo from bar" if I implement the program to let "user" evaluate to "foo", etc.
The current approach I'm thinking of consists of a state machine that eats one character at a time from the string and evaluates the expression after reaching '}'. Any hints or other suggestions?
Note: boost:: is most welcome! :-)
Update Thanks for the first three suggestions! Unfortunately I made the example too simple! I need to be able examine the contents within ${} so it's not a simple search and replace. Maybe it will say ${uppercase:foo} and then I have to use "foo" as a key in a hashmap and then convert it to uppercase, but I tried to avoid the inner details of ${} when writing the original question above... :-)
#include <iostream>
#include <conio.h>
#include <string>
#include <map>
using namespace std;
struct Token
{
enum E
{
Replace,
Literal,
Eos
};
};
class ParseExp
{
private:
enum State
{
State_Begin,
State_Literal,
State_StartRep,
State_RepWord,
State_EndRep
};
string m_str;
int m_char;
unsigned int m_length;
string m_lexme;
Token::E m_token;
State m_state;
public:
void Parse(const string& str)
{
m_char = 0;
m_str = str;
m_length = str.size();
}
Token::E NextToken()
{
if (m_char >= m_length)
m_token = Token::Eos;
m_lexme = "";
m_state = State_Begin;
bool stop = false;
while (m_char <= m_length && !stop)
{
char ch = m_str[m_char++];
switch (m_state)
{
case State_Begin:
if (ch == '$')
{
m_state = State_StartRep;
m_token = Token::Replace;
continue;
}
else
{
m_state = State_Literal;
m_token = Token::Literal;
}
break;
case State_StartRep:
if (ch == '{')
{
m_state = State_RepWord;
continue;
}
else
continue;
break;
case State_RepWord:
if (ch == '}')
{
stop = true;
continue;
}
break;
case State_Literal:
if (ch == '$')
{
stop = true;
m_char--;
continue;
}
}
m_lexme += ch;
}
return m_token;
}
const string& Lexme() const
{
return m_lexme;
}
Token::E Token() const
{
return m_token;
}
};
string DoReplace(const string& str, const map<string, string>& dict)
{
ParseExp exp;
exp.Parse(str);
string ret = "";
while (exp.NextToken() != Token::Eos)
{
if (exp.Token() == Token::Literal)
ret += exp.Lexme();
else
{
map<string, string>::const_iterator iter = dict.find(exp.Lexme());
if (iter != dict.end())
ret += (*iter).second;
else
ret += "undefined(" + exp.Lexme() + ")";
}
}
return ret;
}
int main()
{
map<string, string> words;
words["hello"] = "hey";
words["test"] = "bla";
cout << DoReplace("${hello} world ${test} ${undef}", words);
_getch();
}
I will be happy to explain anything about this code :)
How many evaluation expressions do intend to have? If it's small enough, you might just want to use brute force.
For instance, if you have a std::map<string, string> that goes from your key to its value, for instance user to Matt Cruikshank, you might just want to iterate over your entire map and do a simple replace on your string of every "${" + key + "}" to its value.
Boost::Regex would be the route I'd suggest. The regex_replace algorithm should do most of your heavy lifting.
If you don't like my first answer, then dig in to Boost Regex - probably boost::regex_replace.
How complex can the expressions get? Are they just identifiers, or can they be actual expressions like "${numBad/(double)total*100.0}%"?
Do you have to use the ${ and } delimiters or can you use other delimiters?
You don't really care about parsing. You just want to generate and format strings with placeholder data in it. Right?
For a platform neutral approach, consider the humble sprintf function. It is the most ubiquitous and does what I am assuming that you need. It works on "char stars" so you are going to have to get into some memory management.
Are you using STL? Then consider the basic_string& replace function. It doesn't do exactly what you want but you could make it work.
If you are using ATL/MFC, then consider the CStringT::Format method.
If you are managing the variables separately, why not go the route of an embeddable interpreter. I have used tcl in the past, but you might try lua which is designed for embedding. Ruby and Python are two other embeddable interpreters that are easy to embed, but aren't quite as lightweight. The strategy is to instantiate an interpreter (a context), add variables to it, then evaluate strings within that context. An interpreter will properly handle malformed input that could lead to security or stability problems for your application.