LeetCode //C - 964. Least Operators to Express Number

964. Least Operators to Express Number

Given a single positive integer x, we will write an expression of the form x (op1) x (op2) x (op3) x ... where each operator op1, op2, etc. is either addition, subtraction, multiplication, or division (+, -, *, or /). For example, with x = 3, we might write 3 * 3 / 3 + 3 - 3 which is a value of 3.

When writing such an expression, we adhere to the following conventions:

  • The division operator (/) returns rational numbers.
  • There are no parentheses placed anywhere.
  • We use the usual order of operations: multiplication and division happen before addition and subtraction.
  • It is not allowed to use the unary negation operator (-). For example, "x - x" is a valid expression as it only uses subtraction, but "-x + x" is not because it uses negation.

We would like to write an expression with the least number of operators such that the expression equals the given target. Return the least number of operators used.

Example 1:

Input: x = 3, target = 19
Output: 5
Explanation: 3 * 3 + 3 * 3 + 3 / 3.

The expression contains 5 operations.

Example 2:

Input: x = 5, target = 501
Output: 8
Explanation: 5 * 5 * 5 * 5 - 5 * 5 * 5 + 5 / 5.

The expression contains 8 operations.

Example 3:

Input: x = 100, target = 100000000
Output: 3
Explanation: 100 * 100 * 100 * 100.

The expression contains 3 operations.

Constraints:
  • 2 <= x <= 100
  • 1 < = t a r g e t < = 2 ∗ 10 8 1 <= target <= 2 * 10^8 1<=target<=2∗108

From: LeetCode

Link: 964. Least Operators to Express Number


Solution:

Ideas:
  • For small values v <= x, directly compute the best using only 1s (x/x) or as x minus some 1s.

  • For larger values, find the closest power x^k and try:

    • Undershoot: use x^(k-1) and build the remainder.
    • Overshoot: use x^k and subtract the difference (only if it helps).
  • Use memoization to avoid recomputing subproblems.

Code:
c 复制代码
typedef struct {
    int key;
    int val;
} Pair;

static Pair memo[10000];
static int memoSize;

static int dfs(int x, int v) {
    // Base case: v <= x
    if (v <= x) {
        // Option 1: v = 1 + 1 + ... + 1 (v times)
        //   1 is x / x  -> 1 operator
        //   plus (v - 1) additions
        //   total = v (division) + (v - 1) (+) = 2*v - 1
        int op_add = 2 * v - 1;

        // Option 2: v = x - ( (x - v) ones )
        //   (x - v) ones: 2*(x - v) - 1 operators
        //   one more '-' to subtract from x
        //   total = 2*(x - v)
        int op_sub = 2 * (x - v);

        return op_add < op_sub ? op_add : op_sub;
    }

    // Check memo
    for (int i = 0; i < memoSize; ++i) {
        if (memo[i].key == v) return memo[i].val;
    }

    // Find smallest k such that x^k >= v
    int k = 2;
    long y = (long)x * x;   // y = x^2 initially
    while (y < v) {
        y *= x;
        ++k;               // now y = x^k
    }
    // Now y = x^k >= v, and y/x = x^(k-1)

    // Option 1 (undershoot):
    //   Use x^(k-1) once (cost k-1 multiplications),
    //   then express the remaining (v - x^(k-1))
    int op1 = (k - 1) + dfs(x, v - (int)(y / x));

    int ans = op1;

    // Option 2 (overshoot), only if the "over" part is smaller than v:
    //   Use x^k once (cost k multiplications),
    //   then express (x^k - v), and subtract it.
    if (y - v < v) {
        int op2 = k + dfs(x, (int)(y - v));
        if (op2 < ans) ans = op2;
    }

    // Save to memo
    memo[memoSize].key = v;
    memo[memoSize].val = ans;
    ++memoSize;

    return ans;
}

int leastOpsExpressTarget(int x, int target) {
    memoSize = 0;  // reset memo for each test case
    return dfs(x, target);
}
相关推荐
叶小鸡7 分钟前
小鸡玩算法-力扣HOT100-动态规划(上)
算法·leetcode·动态规划
LuminousCPP14 分钟前
数据结构 - 线性表第三篇:基于顺序表实现 C 语言通讯录(基础功能篇)
c语言·数据结构·经验分享·笔记·算法
_日拱一卒18 分钟前
LeetCode:114二叉树展开为链表
java·开发语言·算法
无小道28 分钟前
Redis——哈希类型相关指令
redis·算法·哈希算法
凌波粒29 分钟前
LeetCode--513.找树左下角的值(二叉树)
java·算法·leetcode
一个不知名程序员www30 分钟前
算法学习入门---算法题DAY1
c++·算法
子琦啊35 分钟前
构造函数、this指向和原型链机制
javascript·算法·贴图
WHS-_-202236 分钟前
Millimeter Wave ISAC-SLAM: Framework and RFSoC Prototype
人工智能·算法·原型模式
kkeeper~37 分钟前
0基础C语言积跬步之内存函数
c语言·开发语言
吃好睡好便好38 分钟前
在Matlab中绘制杆状图
开发语言·学习·算法·matlab·信息可视化