int main() { std::string s = "1^0|0|1"; assert(isValidBoolExpr(s)); // unordered_map requires hash to be defined for custom struct keys std::map<PriorResult, size_t> table; std::cout << s << " has " << countWays(s, false, table) << " ways of parenthesizing to false." << std::endl; assert(2 == countWays(s, false, table)); // 1^((0|0)|1) and 1^(0|(0|1)) return 0; }
long countWays(long n, long cache[]) { if (n == 0) { return 1; }else if(n < 0) { return 0; }else{ cache[n] = countWays(n - 1, cache) + countWays(n - 2, cache) + countWays(n - 3, cache); return cache[n]; } }
int countWays(int n, int memo[]) { if(n<0) return 0; else if(n==0) return 1; else if(memo[n]>-1) //memo[n] already has the value stored. return memo[n]; else { memo[n]=countWays(n-1, memo)+countWays(n-2, memo)+countWays(n-3,memo); return memo[n]; } }
// Driver program to test above functions int main () { int s = 4; printf("Number of ways = %d", countWays(s)); getchar(); return 0; }
// Time: O(n) int countWays1(int n) { int memo[n+1]; int i; for(i=0; i<n+1; i++) memo[i]=-1; return countWays(n, memo); }
void getWays(int nSteps, int ways[]) { ways[nSteps] = countWays(nSteps + 1, 2); }
// Driver program to test above functions int main () { int s = 4, m = 2; printf("Nuber of ways = %d", countWays(s, m)); return 0; }
int countWays(int n) { if (n < 0) return 0; if (n == 0) return 1; return countWays(n-1) + countWays(n-2) + countWays(n-3); }
size_t countWays(const std::string & expr, const bool result, std::map<PriorResult, size_t> & table) { auto seekPriorCalculation = table.find(PriorResult(expr, result)); if (seekPriorCalculation != table.end()) { return seekPriorCalculation->second; } assert(isValidBoolExpr(expr)); if (expr.size() == 1) { // Base case if (expr.compare("1") == 0) { table[PriorResult(expr, result)] = result == true; return (result == true); } else if (expr.compare("0") == 0) { table[PriorResult(expr, result)] = result == false; return (result == false); } else { std::cout << "Expression is ill-formed.\n"; assert(false); } } size_t ways = 0; // Go through and consider each operand as a delimiter of two halves for (auto it = expr.begin(); it != expr.end(); ++it) { if (isOperand(*it)) { auto left = std::string(expr.begin(), it); auto right = std::string(std::next(it, 1), expr.end()); // Count ways to make the left and right side so the operand // achieves the desired result switch (*it) { case '|': { if (result == true) { // Either left, right, or both true ways += countWays(left, true, table) * countWays(right, true, table) + countWays(left, false, table) * countWays(right, true, table) + countWays(left, true, table) * countWays(right, false, table); } else { // Only when both false ways += countWays(left, false, table) * countWays(right, false, table); } break; } case '&': { if (result == true) { // Only when both true ways += countWays(left, true, table) * countWays(right, true, table); } else { // Either left, right, or both false ways += countWays(left, false, table) * countWays(right, true, table) + countWays(left, true, table) * countWays(right, false, table) + countWays(left, false, table) * countWays(right, false, table); } break; } case '^': { if (result == true) { // Both differ ways += countWays(left, true, table) * countWays(right, false, table) + countWays(left, false, table) * countWays(right, true, table); } else { // Both match ways += countWays(left, true, table) * countWays(right, true, table) + countWays(left, false, table) * countWays(right, false, table); } break; } } } } table[PriorResult(expr, result)] = ways; return ways; }
// Driver program to test above algorithm int main(int argc, char **argv) { int s = 4, m = 4; printf("Number of ways = %d", countWays(s, m)); return 0; }