【周赛第69期】满分题解 软件工程选择题 枚举 dfs

目录

  • 选择题
    • 1.
    • 2.
    • 3.
    • 4.
    • 面向对象设计七大原则
  • 编程题
    • S数
    • 最小H值

昨晚没睡好,脑子不清醒,痛失第1名

选择题

1.

关于工程效能,以下哪个选项可以帮助提高团队的开发效率?
A、频繁地进行代码审查
B、使用自动化测试工具
C、使用版本控制系统
D、所有选项都正确

选D。

2.

以下哪个选项不属于编码规范的内容?
A、变量命名规则
B、注释规范
C、代码缩进和格式化
D、数据库表设计

选D。

3.

以下哪个设计原则鼓励我们在实现功能时,尽量对现有代码进行扩展而不是修改?
A、单一职责原则
B、开放封闭原则
C、里氏替换原则
D、接口隔离原则

选B。

4.

关于软件架构设计,以下哪个原则可以帮助我们降低系统的耦合度?
A、单一职责原则
B、开放封闭原则
C、里氏替换原则
D、依赖倒置原则

选D。

面向对象设计七大原则

开闭原则、里氏代换原则、迪米特原则(最少知道原则)、单一职责原则、接口分隔原则、依赖倒置原则、组合/聚合复用原则。

编程题

S数

如果一个正整数 自身是回文数 ,而且它也是一个 回文数平方,那么我们称这个数为 S数。 现在,给定两个正整数
L 和 R(以字符串形式表示),返回包含在范围 [L, R] 中的S数的数目。

我是按自身是回文数枚举的,其实应该按枚举量少的进行枚举,按开平方后的回文数枚举应该会更快。
为了代码简单写的快最后再检查范围。

#include

using namespace std;
using LL = long long;
LL L, R;
int strL[20], strR[20];
int topL, topR;
LL ans = 0;
int str[20];

bool check(int x) {
    int s[20] = {};
    int len = 0;
    while (x) {
        s[++len] = x % 10;
        x /= 10;
    }
    for (int i = 1, j = len; i < j; i++, j--) {
        if (s[i] != s[j])
            return false;
    }
    return true;
}

void dfs(LL now, int step, int base, int len) {
    if (step == base + 1) {
        if (len & 1) {
            for (int i = base - 1; i >= 1; i--) {
                now = now * 10 + str[i];
            }
        } else {
            for (int i = base; i >= 1; i--) {
                now = now * 10 + str[i];
            }
        }
        if (now < L)
            return;
        if (now > R) {
            cout << ans << endl;
            exit(0);
        }
        LL tmp = sqrt(now);
        if (tmp * tmp == now && check(tmp)) {
            ++ans;
        }
        if ((tmp + 1) * (tmp + 1) == now && check(tmp + 1)) {
            //cout<<" "<
            ++ans;
        }
        return;
    }
    if (step == 1) {
        static const int f[] = {0, 1, 4, 5, 6, 9};
        for (int i = 0; i < 6; i++) {
            str[step] = f[i];
            dfs(now * 10 + f[i], step + 1, base, len);
        }
    } else {
        for (int i = 0; i <= 9; i++) {
            str[step] = i;
            dfs(now * 10 + i, step + 1, base, len);
        }
    }
}

int main() {
    cin >> L >> R;
    for (int i = L; i; i /= 10) {
        strL[++topL] = i % 10;
    }
    for (int i = R; i; i /= 10) {
        strR[++topR] = i % 10;
    }
    for (int len = topL; len <= topR; len++) {
        int baseLen = (len + 1) / 2;
        dfs(0, 1, baseLen, len);
    }
    cout << ans << endl;
    return 0;
}

最小H值

给你一个二维 rows x columns 的地图 heights , 其中 heights[row][col] 表示格子 (row,
col) 的高度。 一开始你在最左上角的格子 (0, 0) , 且你希望去最右下角的格子 (rows-1, columns-1)
(注意下标从 0 开始编号)。 你每次可以往 上,下,左,右 四个方向之一移动,你想要找到H值最小的一条路径。 一条路径的 H值
是路径上相邻格子之间 高度差绝对值最大值 决定的。 请你返回从左上角走到右下角的最小H值。

不是只能下、右,一开始想错了。
dfs需要注意避免不必要的重复,才能保证时间复杂度。

#include

using namespace std;
string mp;
int hang = -1;
int lie = 1;
vector<vector<int>> mpp;
vector<vector<int>> dis;

inline char getChar() {
    static int pos = 0;
    if (pos == (int) mp.length()) {
        return EOF;
    }
    return mp[pos++];
}

inline int getInt() {
    int x = 0;
    int f = 1;
    char t = getChar();
    while (t > '9' || t < '0') {
        if (t == '-')f = -1;
        t = getChar();
    }
    while (t >= '0' && t <= '9') {
        x = x * 10 + t - '0';
        t = getChar();
    }
    return x * f;
}

const int f[4][2] = {{-1, 0},
                     {0,  -1},
                     {0,  1},
                     {1,  0}};

bool dfs(int x, int y) {
    if (x == hang - 1 && y == lie - 1) {
        return true;
    }
    for (int i = 0; i < 4; i++) {
        int nx = x + f[i][0];
        int ny = y + f[i][1];
        if (nx < 0 || ny < 0 || nx >= hang || ny >= lie) { continue; }
        int newDis = max(dis[x][y], abs(mpp[x][y] - mpp[nx][ny]));
        if (dis[nx][ny] != -1 && dis[nx][ny] <= newDis) { continue; }
        dis[nx][ny] = newDis;
        //cout<
        dfs(nx, ny);
    }
    return true;
}

int main() {
    cin >> mp;
    for (int i = 0; i < (int) mp.length(); i++) { if (mp[i] == '[') { ++hang; }}
    for (int i = 0; i < (int) mp.length(); i++) {
        if (mp[i] == ']') { break; }
        if (mp[i] == ',') { ++lie; }
    }
    mpp = vector<vector<int>>(hang, vector<int>(lie, 0));
    vector<vector<int>> dp = vector<vector<int>>(hang, vector<int>(lie, 0));
    dis = vector<vector<int>>(hang, vector<int>(lie, -1));
    for (int nowH = 0, nowL = 0; nowH <
                                 hang;) {
        mpp[nowH][nowL] = getInt();
        //cout<
        ++nowL;
        if (nowL == lie) {
            ++nowH;
            nowL = 0;
        }
    }
    for (int i = 0; i < hang; i++) {
        for (int j = 0; j < lie; j++) {
            if (i == 0 && j == 0) {
                dp[i][j] = 0;
            } else if (i == 0) {
                dp[i][j] = max(dp[i][j - 1], abs(mpp[i][j] - mpp[i][j - 1]));
            } else if (j == 0) {
                dp[i][j] = max(dp[i - 1][j], abs(mpp[i][j] - mpp[i - 1][j]));
            } else {
                dp[i][j] = min(max(dp[i][j - 1], abs(mpp[i][j] - mpp[i][j - 1])),
                               max(dp[i - 1][j], abs(mpp[i][j] - mpp[i - 1][j])));
            }
        }
    }
    dis[0][0] = 0;
    dfs(0, 0);
    cout << dis[hang - 1][lie - 1] << endl;
    return 0;
}

你可能感兴趣的:(ACM,CSDN周赛,软件工程,算法,dfs)