图论\dp 两题

3310. 移除可疑的方法 - 力扣(LeetCode)

读懂题目就不难。a,b表示方法a调用了方法b。现在要除去所有的可疑方法,就要把方法k调用的(直接与间接)方法都删除。如果存在非可疑方法调用可疑方法,就不删除任何方法。

思路很简单,建图之后从k开始搜索。dfs或者bfs都可以。注意,有向图没办法用并查集。用并查集判断了k和哪些节点是在一个集合中,但没办法处理这个集合中节点的指向关系。

bfs版本:

cpp 复制代码
class Solution
{
public:
    vector<int> remainingMethods(int n, int k, vector<vector<int>>& invocations)
    {
        //建图
        vector<vector<int>>g(n);
        for (auto& edge:invocations)
        {
            g[edge[0]].push_back(edge[1]);
        }
        //方法edge[0]调用了方法edge[1]

        //bfs找出可疑方法:方法k及其调用的方法
        vector<int>sus(n);
        queue<int>que;
        que.push(k);//从k开始bfs
        sus[k] = 1;//可疑标记为1
        while (!que.empty())
        {
            int curr = que.front();
            que.pop();
            for (int node : g[curr])
            {
                if (sus[node] == 0)//图可能有环,避免死循环
                {
                    sus[node] = 1;
                    que.push(node);
                }
            }
        }

        //检查:是否有非可疑方法调用可以方法,如果有就不能删掉
        for (auto& e : invocations)
        {
            if (sus[e[0]] == 0 && sus[e[1]] == 1)//非可疑方法调用可疑方法
            {
                //则无法移除可疑方法
                vector<int>ans(n);
                iota(ans.begin(), ans.end(), 0);
                return ans;
            }
        }

        //移除可疑方法
        vector<int>ans;
        for (int i = 0; i < n; i++)
        {
            if (sus[i] == 0)
            {
                ans.push_back(i);
            }
        }
        return ans;
    }
};

std::iota用于生成一个连续的数值序列,需要引入numeric库。

cpp 复制代码
template <class ForwardIterator, class T>
void iota(ForwardIterator first, ForwardIterator last, T value);

从T开始赋值。

377. 组合总和 Ⅳ - 力扣(LeetCode)

本质和爬楼梯:70. 爬楼梯 - 力扣(LeetCode)是一样的。只不过,爬楼梯的数组是1,2,即你一次只能爬1或2个台阶。本题nums中元素表示一次能爬的台阶数。在求dpi时,遍历nums数组,假设我们遍历到了j,那么dpi加上dpi-j即可。即到达第i个阶梯有dpi个方法,现在发现还能一次走j个台阶,所以新增方法数等于到达第i-j个台阶的方法数。

cpp 复制代码
class Solution 
{
public:
    int combinationSum4(vector<int>& nums, int target) 
    {
        int n=nums.size();
        vector<unsigned>dp(target+1);
        dp[0]=1;
        for(int i=1;i<=target;i++)
        {
            for(int x:nums)
            {
                if(x<=i) dp[i]+=dp[i-x];
            }
        }
        return dp[target];
    }
};

unsigned避免数据溢出。

相关推荐
暖阳华笺21 小时前
【数据结构与算法】哈希专题
数据结构·c++·算法·leetcode·哈希算法
随意起个昵称21 小时前
区间dp-进阶题目1(进阶合并)
c++·算法·动态规划
AKA__Zas21 小时前
芝士算法(滑动窗口片 2.0)
java·算法·leetcode·学习方法
四代水门21 小时前
LeetCode刷算法题(C++)
c++·算法·leetcode
hai3152475431 天前
一种通过空间几何转换进行软件编程计算的方式与现有计算的对比
人工智能·深度学习·数学建模·硬件架构·几何学·图论·拓扑学
退休倒计时1 天前
【每日一题】LeetCode 53. 最大子数组和 TypeScript
数据结构·算法·leetcode·typescript
2601_961875241 天前
法考资料2026|全套|资料已整理
数据结构·算法·链表·贪心算法·eclipse·线性回归·动态规划
汉克老师1 天前
GESP2026年3月认证C++六级真题与解析(编程题1 选数)
c++·动态规划·线性dp·gesp六级·状态转移·选与不选
洛水水1 天前
【力扣100题】86.柱状图中最大的矩形
算法·leetcode·职场和发展
渡之1 天前
GRiM-Net 深度解析 | 无人机 GNSS 拒止场景下两阶段跨视角视觉定位框架
深度学习·算法·动态规划·无人机