1. 东华OJ基础10-12题概述
东华OJ(Online Judge)是东华大学计算机学院开发的在线编程评测系统,主要用于学生练习编程基础和算法能力。其中基础10-12题是面向初学者的入门级题目,主要考察基本的编程语法、逻辑思维和简单算法的实现能力。
这三道题目虽然难度不高,但对于刚接触编程的同学来说,往往会在一些细节上栽跟头。我在担任ACM校队教练期间,见过太多学生在这几道题上反复提交却无法通过的情况。究其原因,大多是对题目理解不够透彻,或者没有掌握正确的解题方法。
需要模型API调用? 免费领10W Token,多模型网关一键接入 Claude、DeepSeek 等主流模型。
2. 题目10:数字反转
2.1 题目要求分析
题目10要求将一个不超过100位的正整数反转后输出。看似简单,但有几个关键点需要注意:
- 输入的数字可能非常大(最多100位),不能直接用整型变量存储
- 需要考虑前导零的情况,比如输入"1200",正确输出应该是"0021"而非"21"
- 边界条件处理,如输入为"0"时应该直接输出"0"
2.2 解题思路与实现
最稳妥的解法是将数字作为字符串处理。以下是具体步骤:
- 读取输入字符串
- 去除字符串末尾可能存在的换行符
- 使用双指针法反转字符串:
- 初始化左指针i=0,右指针j=strlen(str)-1
- 当i<j时,交换str[i]和str[j]
- i右移,j左移
- 输出反转后的字符串
示例代码(C语言):
c复制#include <stdio.h>
#include <string.h>
void reverseString(char *str) {
int len = strlen(str);
for (int i = 0, j = len - 1; i < j; i++, j--) {
char temp = str[i];
str[i] = str[j];
str[j] = temp;
}
}
int main() {
char num[101];
scanf("%s", num);
reverseString(num);
printf("%s\n", num);
return 0;
}
2.3 常见错误与调试技巧
很多同学容易犯以下错误:
- 使用整型变量存储输入导致溢出
- 忘记处理字符串末尾的换行符
- 反转时错误地跳过了中间字符
调试时可以:
- 打印中间过程,观察字符串变化
- 测试边界条件(如输入"0"、"0001"等)
- 使用strlen检查字符串长度是否正确
3. 题目11:最大公约数与最小公倍数
3.1 题目要求解析
题目11要求计算两个正整数的最大公约数(GCD)和最小公倍数(LCM)。需要注意:
- 输入的两个数范围在1到10000之间
- 需要同时输出GCD和LCM
- 计算效率要求,不能使用暴力枚举法
3.2 算法选择与实现
推荐使用欧几里得算法(辗转相除法)计算GCD,然后利用GCD计算LCM:
GCD计算公式:
gcd(a, b) = gcd(b, a % b) (直到b为0时返回a)
LCM计算公式:
lcm(a, b) = a * b / gcd(a, b)
示例代码:
c复制#include <stdio.h>
int gcd(int a, int b) {
return b == 0 ? a : gcd(b, a % b);
}
int lcm(int a, int b) {
return a * b / gcd(a, b);
}
int main() {
int a, b;
scanf("%d %d", &a, &b);
printf("%d %d\n", gcd(a, b), lcm(a, b));
return 0;
}
3.3 性能优化与边界处理
实际编码时需要注意:
- 确保a > b,否则第一次递归会多执行一次交换
- 处理a*b可能溢出的情况(虽然本题范围不会)
- 特殊处理a或b为0的情况(虽然题目保证输入为正整数)
优化技巧:
- 使用迭代而非递归实现gcd,避免栈溢出
- 先计算gcd再计算lcm,避免重复计算
- 使用位运算优化模运算
4. 题目12:素数判断
4.1 题目要求分析
题目12要求判断一个给定的正整数是否为素数。关键点:
- 输入范围1到10000
- 1不是素数,需要特殊处理
- 需要高效的判断算法
4.2 素数判断算法实现
最基础的实现是试除法,但可以进行优化:
- 排除小于2的数(都不是素数)
- 单独处理2(唯一的偶素数)
- 只需检查到sqrt(n)即可
- 只需检查奇数因子
优化后的实现:
c复制#include <stdio.h>
#include <math.h>
#include <stdbool.h>
bool isPrime(int n) {
if (n < 2) return false;
if (n == 2) return true;
if (n % 2 == 0) return false;
int sqrt_n = sqrt(n);
for (int i = 3; i <= sqrt_n; i += 2) {
if (n % i == 0) return false;
}
return true;
}
int main() {
int num;
scanf("%d", &num);
printf("%s\n", isPrime(num) ? "Yes" : "No");
return 0;
}
4.3 进阶优化与测试技巧
更进一步的优化:
- 预先生成素数表(适用于多次查询)
- 使用Miller-Rabin概率性测试(适用于大数)
- 使用6k±1优化(检查形如6k±1的数)
测试时应该覆盖:
- 边界值:1, 2, 3
- 典型素数:17, 19, 23
- 典型合数:9, 15, 21
- 较大素数:997, 991
- 较大合数:10000, 9999
5. 综合解题技巧与OJ使用建议
5.1 编程规范与调试方法
在东华OJ上提交代码时,建议:
- 使用标准输入输出(scanf/printf)
- 避免使用全局变量
- 添加必要的注释
- 测试所有边界条件
调试技巧:
- 使用printf输出中间结果
- 在本地先测试样例输入
- 仔细阅读编译错误信息
- 对比他人AC的代码
5.2 时间复杂度分析
对于这三道题:
- 题目10:O(n),n为数字位数
- 题目11:O(log(min(a,b)))(欧几里得算法)
- 题目12:O(√n)(优化后的试除法)
理解时间复杂度有助于:
- 预估程序性能
- 选择合适的算法
- 避免超时(TLE)
5.3 常见WA原因与解决方法
Wrong Answer的常见原因:
- 未处理边界条件
- 输出格式错误(如多或少空格、换行)
- 算法逻辑错误
- 数据类型范围不足
解决方法:
- 仔细阅读题目要求
- 编写测试用例
- 使用assert进行断言
- 分模块测试
6. 从基础题到算法进阶
虽然这三题是基础题,但它们涉及的重要编程概念包括:
- 字符串处理
- 递归与迭代
- 数学算法
- 边界条件处理
建议后续学习路线:
- 掌握更多数学相关算法(快速幂、筛法等)
- 学习基础数据结构(栈、队列、链表)
- 练习更复杂的字符串处理
- 尝试动态规划等算法
对于想要进一步提升的同学,可以:
- 尝试用不同语言实现
- 思考更优的解法
- 解决东华OJ上的进阶题目
- 参加编程竞赛锻炼能力
