代码随想录算法训练营后续—图论补充

第一题、最大人工岛 力扣题目链接

class Solution {
private:
    int count;
    int dir[4][2] = {0, 1, 1, 0, -1, 0, 0, -1};  // 上下左右四个方向
    void dfs(vector<vector<int>>& grid, vector<vector<bool>>& visited, int x, int y, int mark){
        if(visited[x][y] || grid[x][y] == 0) return;  // 终止条件,如果访问过或者是遇到海水即终止返回
        visited[x][y] = true;
        grid[x][y] = mark;
        count ++;
        for(int i = 0; i < 4; i++){
            int nextx = x + dir[i][0];
            int nexty = y + dir[i][1];
            if(nextx < 0 || nextx >= grid.size() || nexty < 0 || nexty >= grid[0].size()) continue;  //超出范围
            dfs(grid, visited, nextx, nexty, mark);
        }
    }
public:
    int largestIsland(vector<vector<int>>& grid) {
        int n = grid.size(), m = grid[0].size();
        vector<vector<bool>> visited = vector<vector<bool>>(n, vector<bool>(m, false));
        unordered_map<int, int> gridNum;
        int mark = 2;
        bool isAllGrid = true;  // 标记是否整个地图都是陆地
        for(int i = 0; i < n; i++){
            for(int j = 0; j < m; j++){
                if(grid[i][j] == 0) isAllGrid = false;
                if(!visited[i][j] && grid[i][j] == 1){
                    count = 0;
                    dfs(grid, visited, i, j, mark);
                    gridNum[mark] = count;
                    mark++;
                }
            }
        }
        if(isAllGrid) return n * m;

        // 计算岛屿面积
        int result = 0;  // 存放最后结果
        unordered_set<int> visitedGrid;  //记录访问过的岛屿
        for(int i = 0; i < n; i++){
            for(int j = 0; j < m; j++){
                int count = 1;
                visitedGrid.clear();
                if(grid[i][j] == 0){
                    for(int k=0; k < 4; k++){
                        int neari = i + dir[k][0];
                        int nearj = j + dir[k][1];
                        if (neari < 0 || neari >= grid.size() || nearj < 0 || nearj >= grid[0].size()) continue;
                        if(visitedGrid.count(grid[neari][nearj])) continue;  // 避免重复添加
                        // 周围的岛屿面积相加
                        count += gridNum[grid[neari][nearj]];
                        visitedGrid.insert(grid[neari][nearj]);  // 访问过就标记上
                    }
                }
                result = max(result, count);
            }
        }
        return result;
    }
};

第二题、单词接龙 力扣题目链接

class Solution {
public:
    int ladderLength(string beginWord, string endWord, vector<string>& wordList) {
        unordered_set<string> wordSet(wordList.begin(), wordList.end());
        if(wordSet.find(endWord) == wordSet.end()) return 0; // 目标词不在字典里 直接返回0
        unordered_map<string, int> visitMap;
        queue<string> que;
        que.push(beginWord);

        visitMap.insert(pair<string, int>(beginWord, 1));

        while(!que.empty()){
            string word = que.front();
            que.pop();
            int path = visitMap[word]; // 这个word的路径长度
            for(int i = 0; i < word.size(); i++){
                string newWord = word;
                for(int j=0; j < 26; j++){
                    newWord[i] = j + 'a';
                    if(newWord == endWord) return path + 1;  // 找到目标词 返回路径长度
                    // 在wordset中且没有访问过
                    if (wordSet.find(newWord) != wordSet.end()&& visitMap.find(newWord) == visitMap.end()) {
                        // 添加访问信息
                        visitMap.insert(pair<string, int>(newWord, path + 1));
                        que.push(newWord);
                    }        
                       
                }
            }
        }
        return 0;
    }
};

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值