如何出一道ACM算法题?

本文背景

本人算法能力一般,但是为省赛和区域赛网络赛出过几道题,总结了一些自己的经验,希望与大家分享。本文不涉及具体的算法题,都是一些理论性的想法和一些建议。

题源

如果你能在没有题源的情况下自己想出一道新的题目,想必也很难看到这篇文章了。题源是出题的第一步,相信到了需要出题的地步,正在看这篇博客的你一定有自己熟悉的刷题网站,而这个网站可以作为你的题源,因为熟悉。本人推荐两个题源网站:

英文题源网站 Codeforce

中文题源网站 51nod

拿到的题源一定要确保只能能够写出所有解法,可能题目有O(n^2),O(nlog(n)),O(n)三种解法,如果有的话这三种解法你都要弄会,至少看了别人的答案后自己能够完全透彻理解。

一道题有如下几个组成部分,而作为出题者,关心的不只这几部分:

  1. 题目名。根据出题要求,可以英文或者中文。
  2. 复杂度要求。时间空间复杂度要求,一般时间复杂度更为重要。
  3. 题目描述。也可称为题面或题意,一般会有一个故事来描述情形;也可没有故事,用抽象的数学图形或者操作步骤来描述题目。
  4. 输入、输出格式。一般是输入占几行、输出占几行,输入哪些数据等的描述。
  5. 输入、输出样例。
  6. 题目提示Notes。一般是关于样例的解释,或者特殊格式出题的提示。Notes部分也可省略。

注意:你可能读到一半就去出题了,所以我打算将注意事项预先写在这里。即:你出好的题目一定要保证题目名、题目描述、输入、输出等在百度、谷歌等常用浏览器中都搜不到出题用的题源或者类似的题目。

题意改编

关于题意改编,也就是题目描述部分,以下提供四种策略:

  1. 具体具体化。(描述对象转移)题目可能有具体的某个人或者某件事情,进行某种操作,你可以将这个具体事件或具体的人,转移到最近发生的一些事情,或者你们同学比较熟悉的东西。例如:以你们协会或者小组或者某个老师作为题目的描述对象,这样更能增加题目的趣味性。
  2. 具体抽象化。如果你嫌转移描述对象比较麻烦,你可以将题目抽象为某个抽象地数学模型,图形的排列,碰撞,走迷宫等,直接用数学模型来描述。
  3. 抽象抽象化。也是采用描述对象转移的方法,你可以将某个数学模型,转移到另一个数学模型场景。
  4. 抽象具体化。根据原先抽象加以具体描述。如果原先是一道水题,你可以将这道题改编成英文阅读理解题,不要忘记英文阅读也是ACM算法竞赛的一部分,读懂题目是做题的前置条件。

输入输出改编

  1. 增加题源输入的前置条件,你可以将输入改变成另一组和题源输入相关的输入,来增加题目难度。比如,题源输入的是排序好的数字,你可以将其输入改成乱序。
  2. 减少题源输入的前置条件,直接输入原题处理后出来的数据,将其作为新题的输入。
  3. 针对输出也有以上两种情况,分别对应增加减少难度,不再赘述。
  4. 输入输出还可以从格式角度改编,修改某些条件后输出可以由【模式一】(输入->输出->输入->输出,循环多次)变成【模式二】(输入->输出,所有数据必须一次输入或输出,意味着要增加存储或者增加处理步骤)。当然这个操作也可逆。

复杂度改编

  1. 修改复杂度的要求,卡掉复杂度O(nlogn)以上的解法,增加题目难度。比如,原先要求2000ms,你可以将其改成500ms或者1000ms,具体数值依据具体情况而定,一般是500ms的整数倍。
  2. 修改输入输出要求,增大或减少输入输出的数据量级,让题目更复杂或更简单。
  3. 修改数据大小要求,比如原先数据为10^9,刚好为int型。如果你将数据大小修改为10^18,那就只能用long long型来存,可能会卡掉一些解法;如果你将数据大小修改为10^5,可能会多出一些做法,比如用hash表,然后前缀和、后缀和等处理。
  4. 修改数据类型要求。原先输入为int,你将其改成double或者float,可能会增加一些难度,反之减少难度。

以上为针对题目的修改,一定要确保搜索引擎没法搜索到改好的题目。

如何生成样例

生成输入数据

一般我们需要20组左右的样例,保存在文件中

  1. 首先一定有一些边界输入,需要你自己添加,比如边界情况,特殊情况等等。
  2. 当你添加了数据量相对小的边界输入后,可能有一些数据量大的边界输入无法手动添加,可以写一个代码,添加极限数据量的边界输入。
  3. 剩下的可以写一个代码让python随机生成不同阶次的样例。比如你的数据量大小为10^6,你可以生成数个数据量100、数据量1000、数据量10000、数据量100000、数据量1000000的输入。

生成输出数据

将产生的20组输入样例在你的标准程序中,输出结果在文件中,保存为输出样例。这里一定要保证你的标程的正确性,以及输入输出的合法性(符合题目描述)。

你需要将生成好的输入输出拿出一两组放在题目描述中,当然你可以拿出特殊数据,让参赛者 AC;也可以只拿出常规数据,让做题者一直 WA。生成好的样例规范命名,如下图所示:

这张图片转载自本人CSDN博客:

写标程+OJ服务器实际运行

做完上面这几部之后,一道题目基本上出完了,接下来你需要将这些数据和样例在你们的OJ服务器上运行,确保时间,空间都符合要求。在测试中,你需要将你预想能通过的几种复杂度的解法都在服务器上跑一遍,确保题目的解法可行性。

总结

本人大四的时候给省赛出了一道题目,并不难,但是数据处理等卡住了很多队伍。

我认为让一部分会高级操作、数据处理比较熟悉,或者对时间复杂度优化比较熟悉的题,有区分度的题才是好题。

需要卡住的是那些只会暴力解法的队伍。

本人经验分享结束,暂且只记得这么多了,后面可能还会更新。

希望读这篇博客的你能出出一道让自己和大家都满意的题目。

原文地址:https://www.cnblogs.com/zhangjiuding/p/11334926.html

时间: 2024-08-25 04:08:18

如何出一道ACM算法题?的相关文章

Nim Game,一个有趣的游戏,也是一道入门算法题。

Nim Game,其实很多人都玩过.其实就是我们玩的划线游戏. 一张纸上,画若干条线,双方一人划一次,每次划掉1~3条线.可以选择画1条,也可以划2条,也可以3条.具体划去几条线完全看自己的策略.谁划掉最后一条线,就是赢家. 如上图,蓝方获胜. 正在看这篇文章的你一定是一个聪明人,每一步都是最优解,而你的对手,也跟你一样聪明,每步都是最优的解法. 现在你作为先手,在线条总数为多少的时候,你必赢呢,又在多少的时候必输呢? 可不可以用一个函数来判断在线条总是为x时你的输赢情况呢?这样你以后跟别人玩这

一道约瑟夫算法题的简单设计

说约瑟夫问题,网上是有一大堆各种各样的文章,想必也给出了各种各样的代码,但这却不能阻挡我写这篇博文的心啊,要知道我才刚刚开通个博客不写点什么总觉得空虚.... 那么就先来讲一下我所要解决的问题:N个人围坐成一圈,从1开始顺序编号:游戏开始,从第一个人开始由1到m的顺序报数,报道m的人退出圈外,问最后留下来那个人原来的序号. (百度了一下发现,原题目不是推出圈外而是"39个犹太人决定宁愿死也不要被敌人抓到,于是决定了一个自杀方式"...) 好吧回归正题,我们继续讲这个算法. 在这里我们用

笔试题82.新浪微博算法题

这是我在面试过程中遇到的一道代码算法题,需要我在一定的时间内完成这个题目,题目的描述: 将某字符串str1中的字符串str2,全部替换成字符串str3. 例如:str1="abcecbbccefgxyzbcgbcg", str2="bc", str3="xy". 替换后为"axyecbxycefgxyzxygxyg" 请尽可能考虑各类情况,并保证时间复杂度和空间复杂度最优. 这个题看似简单的做法是可以的解决的,我当时也想过简单

一天一道算法题--6.5--数学题

感谢 微信平台: 一天一道算法题 ---每天多一点进步---- 话说 这题 我百度了一下 没找到哪个OJ 有出这题 下次 来给我们的学弟学妹们把.... 那我来说下题目大意: 给你一个n 问你从1,2,3--n中选出3个数 能够构成多少种不同的三角形 比如N=5 可以有(2,3,4)(2,3,5)(3,4,5)三种 输入:(3<=n<=n1000000) 输出:种类数 首先 既然是做acm 那么 一般暴力 都直接放弃吧 这里也需要O(n^3)  GG 这里 微信提供的分析 很好  我相信 你慢

一天一道算法题---6.26---二分查找

感谢微信平台---一天一道算法题----每天多一点进步-- 好累啊  现在在用win7自带的输入法 打起来真麻烦 快点把这2天的搞完就重装了 还是直接来源于----〉 待字闺中 分析 给定一个数组A,其中有一个位置被称为Magic Index,含义是:如果i是Magic Index,则A[i] = i.假设A中的元素递增有序.且不重复,请给出方法,找到这个Magic Index.更进一步,当A中允许有重复的元素,该怎么办呢? 没有重复元素的情况 一些同学在遇到这个题目的时候,往往会觉得比较简单.

一天一道算法题---6.27---二分图

感谢微信平台---一天一道算法题---每天多一点进步--- Ah... last... 也很晚了 快2点半了 C罗也告别这届世界杯了  主要还是输给德国太多球了 美国也没赢 唉 还是来源于----> 待字闺中 原题 大家都知道facebook用户都是双向的好友,a是b的好友,那么b一定是a的好友,现在给定一个用户列表,其中有些用户是好友,有些不是,请判断,这些用户是否可以划分为两组,并且每组内的用户,互相都不是好友.如果能,请给出这个划分. 例子1: 用户:{1, 2, 3} 好友关系:1-2,

前端面试的一道算法题

(使用canvas解答) 下面说一个跟前端有点相关并且有点趣的一道算法题. 题目: 平面上有若干个不特定的形状,如下图所示.请写程序求出物体的个数,以及每个不同物体的面积. 分析 想要知道有多少个图形,想到的就是先获取图片中的每一个像素点然后判获取像素点的背景颜色(RGBA).想要获得图片中的每一个像素点,那就可以联想到使用h5的canvas.如下: 菜鸟教程中canvas的getimagedata方法http://www.runoob.com/tags/canvas-getimagedata.

一道看似非常难的面试算法题

这是昨天面试百度时碰到的一道算法题:任意数分三组,使得每组的和尽量相等.由于时间仓促,加之面试时头昏脑涨,这道题没做出来甚至没有给出思路,这让我多少有些遗憾和不甘.因为最近接触算法的东西较多而且本身对算法感兴趣,所以回家之后绞尽脑汁想把这题做出来.其实刚看到这题时感觉不难,但是因为数字个数及数值的不确定,我感觉这题越想越难.昨天一晚上没有睡好,甚至做梦都在想这题! 今天上午在多个群里问了这题,都没有给出思路,真是绝望至极.很多人都说 n/3 的思路,其实这种思路一开始就是死胡同.本人属于那种不会

一天一道算法题--6.19--二分搜索

感谢微信平台---一天一道算法题---每天多一点进步 这是昨天的 只贴下题目 == 再把今天的也是一样处理了   这2天 不想写 可能晚上会有改变吧.. problem: 给定一个最多包含40亿个随机排列的32位 二进制的无符号整数 找出不在文件中的数.显然 由于 2^32=4294967196大于4亿 所以缺少的数不止一个 现限制只能使用几个外部的临时文件和仅几百个字节的内存. ****************************** 过了明天 就没事了 =-= 一天一道算法题--6.19