技巧—对拍

前排警示

------Warning-------

这篇博文在没有注明的情况下,仅适用于windows环境下无Python的对拍。

对拍是一项耗时的工程,其代码量可能会在正解代码的一倍甚至有余。因此,在进行对拍前,请确保以下工作已经完成

  • 编译
  • 测试样例
  • 手写几组小样例,包括特殊情况、极限和边界等
  • 暴力程序(它可以超时,但必须具有正确性)
  • 小黄鸭自查法

注意:简单对拍适应于题目数据简单的题目。当题目涉及图论等,数据生成会产生难度。(假设所使用的环境不包含Python)

前置准备

  • 待检测的程序
  • 标准/暴力程序
  • 数据生成器
  • 对拍脚本(bat)

脚本编写原理

这里提到的是脚本所实现的流程。

  1. 生成数据
  2. 运行标准/暴力程序得出答案
  3. 运行待测程序,得出待测输出
  4. 比较答案与输出
  5. 若正确,继续执行。否则停止程序并报告错误。

基于windows下的精简对拍脚本

此处,我们指定一些文件名,以便下文使用

gen.exe为数据生成器   test.in为保存的生成数据

std.exe为标准/暴力程序  test.ans为正解输出

work.exe为待测程序  test.out为待测输出

@echo off
:loop
gen.exe>test.in
std.exe<test.in>test.ans
work.exe<test.in>test.out
fc test.out test.ans
if not errorlevel 1 goto loop

随机数据生成器

------因为博主很懒,所以这里免去测试截图。直接叙述结论。

这是比较头疼,也大概是难点。因为在c++中,并没有random这种函数。如果直接调用rand,那么每次生成的序列是完全相同的。

如何解决这个问题?我们可以想到使用随机数种子。但难办的是,对于同样的种子,其生成的随机数序列依然相同。

于是我们需要去不断随机修改种子,来达到生成随机数据的目的。

那么本篇推荐用时间作为随机数的种子。这样就可以做到随着时间的改变,随机数不断变化的目的。

故:这种随机数的生成方法,需要用到 time()函数和srand() 、rand()函数

如以下代码,完成了随机生成两个最小为1,最大为16位数的随机数。

#include<iostream>
#include<time.h>
#include<stdlib.h>
using namespace std;
int main(){
     srand( (unsigned)time(NULL) );
     unsigned int a,b;
     a=(rand()<<16)+rand();
     b=(rand()<<16)+rand();
     a%=100000+1;
     b%=100000+1;
     cout<<a<<endl<<b;
} 
原文地址:https://www.cnblogs.com/Uninstalllingyi/p/11279382.html