I am writing library which allows some function programming operations on ranges. Ranges are generalization of STL containers. My question is what result of folding for empty range should be?
auto r = range(4); // lazy numeric range {0,1,2,3}
auto r0 = range(0); // empty range {}
vector<string> vs {"a", "bb"};
vector<string> vs0 {};
// this is obvious and implemented part
cout << (r || add); // 6, || - folding op
cout << (r0 || add); // 0
cout << (vs || add); // "abb"
cout << (vs0|| add); // ""
cout << (r || mul); // 0
cout << (r0 || mul); // 1
cout << (r || max); // 3
// What result of these should be?
cout << (r0 || div); // ???
cout << (r0 || sub); // ???
cout << (r0 || max); // -∞ ???
cout << (r0 || min); // +∞ ???
cout << (r0 || ???); // result of arbitrary op?
EDIT - ANSWER
http://en.wikipedia.org/wiki/Identity_element
I assume your "folders" are instances of some template, with a binary function attached and maybe an initial value.
Traditionally, fold is defined as recursively calling said binary function on (initial, first), then (old value, next) until you run out of stuff to call it on.
There is no such initial value such that subtraction and division work the way you might expect them to (such that fold({1,2}) is 1/2).
Thus "folders" of subtraction and division are either "sums of inverse" and "product of inverse" (ie, fold(r) = 1/fold(r), and fold(r) = -fold(r), which seems pretty boring), or they are fundamentally different things that don't work on empty containers.
max and min should clearly generate the highest and lowest value for a given type, or be the folders of the second type that do not make sense on empty containers.
By "not work", they could throw an exception, or they could return something like a boost::optional<T> -- ie, on an empty list, they do not return anything.
Your folder type could take a function which finds the initial value for a given type, which should resolve to a traits template class or a free function (similar to std::begin).
...
Edit: from the comments below, an improvement to the answer.
The real trick here is that there is no left-hand identity for subtraction and division But there is a right hand identity!
Operations that only have a right hand identity should be expressed as right-hand folds, and operations that only have a left hand identity should be expressed as left-hand folds (aka, foldr and foldl)
Ie, the natural way to express a fold on a list {a,b,c} with identity id of binary operation *op* is:
( (id *op* a) *op* b ) *op c
but for operations without a left-hand identity, this doesn't work.
However, if you reverse the fold handedness, you get this:
a *op* (b *op* (c *op* id))
which works so long as you have a right-hand identity.
This is important for div and sub -- div has a right-hand identity of 1, and sub has a right-hand identity of 0, but neither has a left-hand identity. (there is no element e such that e-x = x for all x. There is an element e such that x-e = x for all x, namely 0).
The same is true of exponentiation (which has a right-hand identity of 1, but no left-hand identity).
This still doesn't match what a naive expectation of what fold div should do. It works on lists of length 2, but on lists of length 3 something unintuitive happens. But at least it is mathematically sound. :)
Related
The output should be false, as false&&true is false. However, the compiler is giving 1 as output.
#include<iostream>
using namespace std;
int main()
{
int a = 10;
int b = 13;
bool flag = true;
cout << ((b - 4) < a) && !flag;
return 0;
}
This is because << has higher precedence than &&, your expression should be:
cout << (((b-4)<a) && !flag);
A more detailed explanation:
One of the first things that any C++ compiler does when processing your source code is to construct an abstract syntax tree (AST) representing your source code. The AST is a tree structure that encodes -among other things- the precedence of different unary and binary operators. An AST for the expression you have written (cout << ((b - 4) < a) && !flag;) would look something like this:
&&
/ \
<< !
/ \ \
cout < flag
/ \
- a
/ \
b 4
How do we know that e.g. && must be the root of the AST or that sub-expressions in parentheses are evaluated first? Because the C++ operator precedence rules say so. These are similar to the rules we use when doing math on paper (e.g. do multiplication before addition) but extended to all operators supported by the language.
We can use the AST to see in what order the sub-expressions of this expression are evaluated, the general rule being that evaluation happens in "bottom up" order, i.e. from the leaves to the root of the AST. In this particular case, evaluation could (conceptually) happen like this:
// left subtree
b - 4 = 9
9 < a = true
cout << true = cout (operator<< returns a reference to cout)
// right subtree
!flag = false
And finally we're left with cout && false. cout implements operator bool which allows it to be implicitly cast to bool, yielding true if the stream has no errors. Because that is the case here, we finally have true && false == false the value of which is unused.
So you can see that your program outputs 1 because during evaluation of the left subtree, cout << true is executed. Afterwards, cout && !flag, though well formed, essentially does nothing because it has no side effects and you don't use the result.
SO I have the equation (( c + ~d ) * b ) * ~( d + a * e ) of which I'm trying to generate a truth table but I'm unsure how I would even start with getting the program to compute whether or not the the variable should be equal to true or false according to the truth table. Any suggestions as how to do this? Thank you in advance.
#include<iostream>
using namespace std;
bool checkBoolTF(int a){
bool TF;
if(a == 0){
TF = false;
}
else{
TF = true;
}
return TF;
}
int main()
{
int a,b,c,d,e;
bool aBool, bBool, cBool, dBool, eBool;
string equation = "(( c + ~d ) * b ) * ~( d + a * e )";
bool equationTF;
//LOOP TO TRUTH TABLE - FINAL VALUES
cout << "----------------------------------------------------------------------" << endl;
cout << "| a | b | c | d | e | " << equation << " |" << endl;
cout << "----------------------------------------------------------------------" << endl;
for(a=0;a<=1;a++){
checkBoolTF(a);
for(b=0;b<=1;b++){
checkBoolTF(b);
for(c=0;c<=1;c++){
checkBoolTF(c);
for(d=0;d<=1;d++){
checkBoolTF(d);
for(e=0;e<=1;e++){
checkBoolTF(e);
cout << "| " << a << " | " << b << " | " << c << " | " << d << " | " << e << " | " << equationTF << " |" << endl;
cout << "----------------------------------------------------------------------" << endl;
}
}
}
}
}
return 0;
}
Step 1: Tokenize.
enum class TokenType {
bracket, binop, binaryop, var, literal
};
struct Token {
TokenType type;
char value;
};
convert the string to a vector of token.
You aren't using literal yet: it is the values 0 or 1. You'll use it later.
Write code that pretty prints a vector of tokens.
Step 2: make a simple tree.
struct Tree {
bool is_token=true;
Token token;
std::vector<Tree> tree;
};
change your first code to generate a tree, containing a vector of tokens.
Write code that pretty prints it. Test.
Step 3: Reduce the tree
Step 3a: Brackets
Now do a reduction step; walks a vector of trees and generates one. It copies everuthing that isn't a bracket blindly to the output. If it sees a ( it copies everything until the matching ) (count open and closed) into a sub-tree, then copies that sub-tree into the output.
It takes "a ( b c )" and makes it a then b c in a subtree.
Write code that can pretty print subtrees. Test.
Step 3b: nested brackets
Next, recurse on the subtree you make, so its nested brackets also get put into subtrees.
Step 3c: operators
Next, work on operators. ~ is easy: it swallows the next tree in the vector. As + binds loser than *, for each + make two subtrees; one for everything before, one for everything after. Then do a pass dping the same for *.
After all this, you turn
a+(b+c)*~(d+e)
into
+ (a , ( * (+ (b, c), ~(+(d,e))))
Step 4: substitute
Map a std::map that maps the variable to a value. Take a copy of a tree, and walk it replacing each variable with a literal equal to its value.
Step 5: evaluate
For each operator, evaluate the subtree(s) then apply the operator.
The result should be a 0 or a 1.
4 and 5 can be done independently by starting with a literal expression.
So I have a personal program that implements this for a strings with a form
"Ab|c(d|E)|fa"
my full source code is a complete mess and contains serveral other things I'm trying to do at the same time (failling to simplify the expression by circling kmaps and stuff)
However I can walk through what I've done if it helps
its setup to be easier for me to parse with capitals representing positive and lower case letters representing negation/not () representing sub expressions and [] representing negated sub expressions
so the input string `"ABC(DEF)G(HI(KK)S[as][ge])S" is converted into this .repr() structure
AND(
A
B
C
AND( D E F )
G
AND(
H
I
AND( K K )
S
NAND( !A !S )
NAND( !G !E )
)
S
)
and something like "Ab|cb" is
OR(
AND( A !B )
AND( !C !B )
)
I have a object (I call expression) that contains information about its type stored in something like the following
namespace xpr { //expression types
enum typ {
identity_,
negation_,
and_,
or_,
nand_,
nor_
};
}
class expression{
...
xpr::typ type = xpr::identity_;
char value = ' ';
std::vector<expression> sub_expressions;
...
};
and either a char that is its value or a vector of expressions. (and or nor nand expressions)
Parsing it into this expression form is done through nested constructors that keep passing the current position in the string as well as its level.
finally to answer your question
std::vector<char> vars = trackUsed();
// equivalent to a set but more efficent to do the sort/unique at the end one time.
removeDuplicates(vars);
const auto truth_table_width = vars.size();
const auto truth_table_size = (size_t)std::pow((size_t)2, truth_table_width); // 2^width
expression::test_type test; // abc through !a!b!c
test.reserve(truth_table_width);
for ( const auto &v : vars ) {
// value_type is value: 6, sign: 2 so character has to fit in 6bits and sign in 2.
// minus 'A' to make A-Z 0-26
test.emplace_back(v - 'A', xpr::negative);
}
for ( size_t i = 0; i < truth_table_size; i++ ) {
for ( size_t j = 0; j < truth_table_width; j++ ) {
// converts 0 to negative and 1 to positive
test[j].sign = (xpr::sign_type)((i >> j) & 0x1);
}
bool valid = testValues(test);
if ( valid ) {
sum_of_products.push_back(test);
}
}
I set up a truth table by extracting all the characters used removing duplicates and sorting them. making a vector<vector< implmentation defined object >>
incrementing a value to the max truth table width and using the sign bit of that value to populate the truth table - 0 = [0, 0, ... 1 = [1, 0, ... 2 = [0, 1, ... etc
and then looping through the outer vector and sending the inner vector to a "testValues" member function that is specialized for each expression type
// given A true B true C true see if whole expression evaluates to true.
bool expression::testValues(const potion::test_type& values) const {
if ( this->is_simple() ) {
auto val = std::lower_bound(values.begin(), values.end(),
this->value,
[ ](potion::val_type lhs, char rhs) -> bool {return lhs < rhs; }
);
if ( type == xpr::identity_ ) return (*val).sign;
if ( type == xpr::negation_ ) return !(*val).sign;
}
if ( type == xpr::and_ || type == xpr::nand_ ) {
const bool is_and = type == xpr::and_; //used to combine and and nand expressions and return the oposite val for nand
for ( const auto& e : sub_expressions ) {
if ( e.testValues(values) == false ) return !is_and; // short circuit- if b is false then abc is false
}
return is_and;
}
if ( type == xpr::or_ || type == xpr::nor_ ) {
const bool is_or = type == xpr::or_; //used to combine or and nor and return the oposite val for nor
for ( const auto& e : sub_expressions ) {
if ( e.testValues(values) == true ) return is_or; // short circuit- if b is true then a|b|c is true
}
return !is_or;
}
throw std::runtime_error("Expression can't be simplified. Type not valid"); //should never happen
return false;
}
There's obviously tons and tons of boilerplate code/ parsing code that's probably not the best. And if you want to parse strings using the "custom language" you are defining "(( c + ~d ) * b ) * ~( d + a * e )"
then the parsing code will obviously be a lot different.
Anyway I hope this is helpful for your project. TLDR: might be a bit harder to implement than you initially thought. Although everything I've done is functional the code isn't the cleanest and its heavly setup for my specific case- only obtaining the truth table entries that have are positive and storing them in a sum of product that can be processed further.
For a start, you can simplify the checkBoolTF function to something like:
bool checkBoolTF (int a)
{
return !(a==0);
}
Secondly, it seems like in the for loops, the values returned by this function are not being assigned to anything and are therefore lost. So you probably want to define an aux variable:
bool auxA = checkBoolTF(a);
and so on..
I would like to show an additional, already existing solution. It is well structured and commented. It is published at github. Please see here
The intended purpose of this program is to calculate MCDC test pairs. But it does of course also all that you want. I do not recommend to copy and paste, but you could read and learn, how to do your implementation.
This code reads exactly the strings that you specified. It also creates a truth table. But this is only a minor part of the whole functionality.
So, what you need to do, is, to compile the string in something that could can be evaluated as a boolean expression.
For that, I first defined the input alphabet and the language, described by a grammar. Then, I created a compiler, consisting of a scanner (lexer), parser and code generator. Actually I created 2 compilers, with the same front end and 2 different back ends. So, 2 different code generators. One, for a virtual machine that can evaluate the boolean expression for any combination of input variables. And, the 2nd backend, will create an abstract syntax tree, with which I evaluate all possible MCDC test pairs.
As said, the first code generator creates Op code for a virtual machine. With this machine, the truth table and with that all minterms are calculated. Then Quine and McCluskey is used (2 different implementations) to minimize the boolean expression. And at the end, and optimzed version of Petricks method is used to solve the unate coverage problem and identify the minimum set of prime implicants.
The MCDC part is maybe a little bit too complex to explain here.
But the main message is, that you first need to parse your string and convert it in something executable.
Then you can evaluate whatever you want.
I am currently learning from an SDL2/OpenGL2 example code, for ImGui. Then, I ran into a line (and a few more alike) as shown below. I believe this part binds SDL mouse events to IMGUI API. However, I do not quite understand how it works.
io.MouseDown[0] = g_MousePressed[0] || (mouseMask & SDL_BUTTON(SDL_BUTTON_LEFT)) != 0
where,
ImGuiIO& io = ImGui::GetIO();
bool mouseDown[5]; // a member of ImGuiIO struct
static bool g_MousePressed[3] = { false, false, false };
Uint32 mouseMask = SDL_GetMouseState(&mx, &my);
(I hope above is enough information...)
What makes me the most confused is the the last part, not equal to 0. I could understand it, if it was a simple assignment of the result of an And and an Or operations. However, there is not equal to zero following at the end and I have not seen this before. I would like to get some help to understand this code please.
expression != 0
is a boolean expression and thus evaluates to either true or false which can be converted to integer values of 0 or 1.
#include <iostream>
int main() {
constexpr size_t SDL_BUTTON = 5;
for (size_t mouseMask = 0; mouseMask < 16; ++mouseMask) {
std::cout << mouseMask << ' '
<< (mouseMask & SDL_BUTTON) << ' '
<< ((mouseMask & SDL_BUTTON) != 0) << '\n';
}
}
Live demo: http://ideone.com/jcmosg
Since || is the logical or operator, we are performing a logical comparison that tests whether io.MouseDown != 0 or (mouseMask & SDL_BUTTON(SDL_BUTTON_LEFT)) != 0 and yields a boolean value (true or false) promoted to whatever type io.mouseDown[0] is.
The code could actually have been written as:
io.MouseDown[0] = g_MousePressed[0] || (mouseMask & SDL_BUTTON(SDL_BUTTON_LEFT))
or
const bool wasPressed = g_mousePressed[0];
const bool newPress = mouseMask & SDL_BUTTON(SDL_BUTTON_LEFT);
const either = (wasPressed == true) || (newPress == true);
io.MouseDown[0] = either;
or
if (g_mousePressed[0])
io.MouseDown[0] = 1;
else if (mouseMask & SDL_BUTTON(SDL_BUTTON_LEFT))
io.MouseDown[0] = 1;
else
io.MouseDown[0] = 0;
See http://ideone.com/TAadn2
If you are intending to learn, find yourself a good sandbox (an empty project file or an online ide like ideone.com etc) and teach yourself to experiment with pieces of code you don't immediately understand.
An expression a = b || c!=0 means a = (b!=0) || (c!=0). In boolean logic, b and b!=0 are equivalent. That's what I think the most confusing part. Once this is understood, there should be no problem.
Note that this expression should not be confused with a=b|c!=0, where | is a binary operation called "bit-wise or", as opposed to the logical operation ||, which is the logical "or". When doing b|c!=0, c!=0 is calculated first to yield a logical value 0 or 1, then b|0 or b|1 is calculated to do nothing (first case) or reset the last bit of the binary code of b to 1 (second case). Finally, that result is assigned to a. In this case, b and b!=0 are not equivalent, because the bit-wise or | is used instead of the logical or ||.
Similarly, & is the "bit-wise and" operator, while && is the logical "and". These two should not be confused either.
Notice that != has a higher precedence than ||, so the whole expression is indeed a simple assignment of the result of an OR.
The !=0 part is a way to turn the result of applying a bitmask into bool, as #AlekDepler said. Funny thing is its pretty much redundant (if mouseMask is of built-in integral type) as implicit conversion from say int to bool works exactly like !=0.
Is it possible to write a one line if-else statement (i.e. only using one ;) without using the ?: expression? For instance something of the form:
if (p == 1) " " else "\n";
Potential purpose could be:
cout << if (p == 1) " " else "\n";
Just curious if this is possible, don't know if there are any practical applications for this.
Thanks
You're asking "how do I do X, without using any of the tools the language provides to do X". It's silly.
And the answer's no. It's not possible.
This doesn't address the general question, but it does work for the specific example you provided.
std::cout << " \n"[(bool)(p - 1)];
Explanation:
First, a string literal (such as " \n") is an array. As such, it participates in pointer decay, and can be indexed just like any other pointer or array.
Second, an integer can be converted to a bool, and the conversion has the special property that a zero is converted to false, and anything else is converted to true. So when I subtract 1 from p, then convert it to bool, it is false if p is 1, and true otherwise.
Third, a bool can be (implicitly) converted back to an integer. false converts to 0, and true converts to 1. So converting from an int to a bool and back has the result that a 0 stays a 0, and anything else becomes a 1.
So, with those three points taken into consideration, the expression:
" \n"[(bool)(p - 1)]
results in one of these two possibilities:
" \n"[0] // a space (if p == 1)
" \n"[1] // or a newline (if p != 1)
I'd downvote this answer if I could.
You already used the two important words that are key to undestand why what you intend is not possible, but you probably haven't grasped their full meaning: Statement and expression.
The if statement (like all statements) does not yield a value, while the ?: operator is an expression that does yield a value.
Distinguishing between statements and expressions is a fundamental concept that is worth learning (check out the links in this answer and take your time!), not just for C++ but for almost all programming languages.
cout << [=]{ if (p == 1) return " "; else return "\n"; }();
Basically: no, it's not possible to do this:
cout << if (p == 1) " " else "\n";
That is exactly the purpose of ?: operator - it yields value. Some things may not be possible with if-else syntax. Example: conditional initialization. Consider:
if(p == 1)
int value = 1; //local variable!
else
int value = 0; //and so is this one!
//here 'value' is unknown
Above problem could be solved this way:
int value; //default initialization
if(p == 1)
value = 1; //assignment to already initialized variable!
else
value = 0; //and so is this!
But these two are not equal. For some types, it may result in totally different behavior, because initialization is different from assignment. ?: is a solution:
int value == (p == 1) ? 1 : 0; //'value' is initialized with value, that depends on 'p'
Do not try to do things without tools, that were designed to do that things for you.
I have a sample midterm question that I am not too sure about. Here it is:
#include <iostream.h>
void f( int i )
{
if( i = 4 || i = 5 ) return;
cout << "hello world\n" ;
}
int main()
{
f( 3 );
f( 4 );
f( 5 );
return 0;
}
So I understand that the logical OR operator has a higher precedence and that it is read left to right. I also understand that what's being used is an assignment operator instead of the relational operator. I just dont get how to make sense of it all. The first thing the compiler would check would be 4 || i? How is that evaluated and what happens after that?
Let's add all the implied parentheses (remembering that || has higher precedence than = and that = is right-associative):
i = ((4 || i) = 5)
So, it first evaluates 4 || i, which evaluates to true (actually, it even ignores i, since 4 is true and || short-circuits). It then tries to assign 5 to this, which errors out.
As written, the code doesn't compile, since operator precedence means it's i = ((4 || i) = 5) or something, and you can't assign to a temporary value like (4 || i).
If the operations are supposed to be assignment = rather than comparison == for some reason, and the assignment expressions are supposed to be the operands of ||, then you'd need parentheses
(i = 4) || (i = 5)
As you say, the result of i=4 is 4 (or, more exactly, an lvalue referring to i, which now has the value 4). That's used in a boolean context, so it's converted to bool by comparing it with zero: zero would become false, and any other value becomes true.
Since the first operand of || is true, the second isn't evaluated, and the overall result is true. So i is left with the value 4, then the function returns. The program won't print anything, whatever values you pass to the function.
It would make rather more sense using comparison operations
i == 4 || i == 5
meaning the function would only print something when the argument is neither 4 nor 5; so it would just print once in your example, for f(3).
Note that <iostream.h> hasn't been a standard header for decades. You're being taught an obsolete version of the language, using some extremely dubious code. You should get yourself a good book and stop wasting time on this course.
The compiler shall isuue an error because expression 4 || i is not a lvalue and may not be assigned.
As for the expression itself then the value of it is always equal to true because 4 is not equal to zero.