[OI] Testlib
Testlib 是用于实现 SpecialJudge 的一种方式
为了使用 Testlib,你需要在你的文件中引用 Testlib.h
testlib.h 下载
使用 Testlib 程序
以 Testlib 的 check 功能示例(实际上 Tesklib 不止可以实现 check 功能)
首先你需要正确的引用到 testlib.h,一般有以下两种方式
- 直接丢到编译器的 
MinGW/include目录下 - 直接丢到源代码目录下(需要用双引号引用)
 
或者你也可以直接写具体路径,比如 #include "C:/Desktop/testlib.h" 之类的
或者使用相对路径
相对路径就是基于当前文件夹向前或向后翻的一种路径,比如对于如下目录结构:
-Desktop
    -Folder1
        -Folder2
            -file.cpp
    -Folder3
        -Folder4
            -testlib.h
假若你想要在 file.cpp 中引用到 testlib.h,你也可以这么写:
#include"../../Folder1/Folder2/testlib.h"
其中 ../ 表示返回上级目录
在将下发的 checker.cpp 程序编译完成后,就可以按照如下格式进行 checker
(一般来说是在终端中进行编译运行,进行之前请先跳到 checker 所在目录,并请将其他文件也放进去)
Windows checker.exe input output answer
Linux ./checker input output answer
input 题目的输入文件,这个文件也可以用数据生成器跑出来
output 你的程序的输出文件
answer 答案文件 一般情况下,你写对拍的时候是拿不到这个答案文件的,但是你仍然可以检验一部分正确性:比如通过模拟能判断出来的部分,或者是格式检验的部分。这就需要考验你对 checker 进行改写的能力了。一般在这种情况下,你完全可以在 answer 位置传一个无关紧要的文件,或者直接把 output 传进去,但是不能空着
在使用 checker 跑对拍的时候,你可能需要判断什么时候应该 pause,事实上是这样判断的:
在调用 cmd 或 Linux 终端的时候,system() 函数实际上是有返回值的,它返回的是程序主程序的 return 值。而 testlib.h 会在正确时返回 0,出现错误时返回 1,因此你可以通过这一点来判断正确性,即这么写:
if(system("checker.exe input output answer")){
    system("pause");
}
编写 Testlib 程序
显然,你不应该使用标准输入输出函数(交互题等特殊题型除外),而应该使用 testlib 提供的读入函数
你需要在主函数使用入下内容以初始化 testlib
int main(int argc, char* argv[]) {
    registerTestlibCmd(argc, argv);
}
此外,testlib 不支持使用 <random> 下的大部分内容,如果你真的要用 rand(),testlib 提供了两种方法:
- 使用 mt19937
 - 使用内置函数
 
关于内置函数
 * Use "shuffle", and "rnd.next()" instead of them
 * because these calls produce stable result for any C++ compiler. Read
 * sample generator sources for clarification.
 *
 * Please read the documentation for class "random_t" and use "rnd" instance in
 * generators. Probably, these sample calls will be useful for you:
 *              rnd.next(); rnd.next(100); rnd.next(1, 2);
 *              rnd.next(3.14); rnd.next("[a-z]{1,100}").
关于文件读入,上述传入的三个文件,分别对应了三个 ifstream 类型的类,分别命名为:
inf 对应 input
ouf 对应 output
ans 对应 answer
它们的读入函数如下所示:
| 函数 | 功能 | 
|---|---|
| char readChar() | 读入一个 char | 
| char readChar(char c) | 限定读入字符,不符合则判为 _wa | 
| char readSpace() | 读入一个空格 | 
| string readToken() | 读入一个字符串,遇到空格、换行、eof 为止、 | 
| long long readLong() | 读入一个 longlong | 
| long long readLong(long long L, long long R) | 限定读入范围(包括 L,R),超出则判为 _wa | 
| int readInt() | 读入一个 int | 
| int readInt(int L, int R), | 限定读入范围(包括 L,R),超出则判为 _wa | 
| double readReal() | 读入一个实数 | 
| double readReal(double L, double R), | 限定读入范围(包括 L,R),超出则判为 _wa | 
| double readStrictReal(double L, double R, int minPrecision, int maxPrecision), | 限定精度范围(包括 L,R),超出则判为 _wa | 
| string readString() | 读入一个字符串 | 
| string readLine() | 读入一行 string,到换行或者 eof 为止 | 
| void readEoln() | 读入一个换行符 | 
| void readEof() | 读入一个 eof | 
| int eof() | 已到达文件末尾则返回 1 | 
关于判定,使用以下三个函数
quitf(st,...) 第一个参数用来传入参数,告诉程序该答案正确还是不正确,有两种,一种为 _ac,一种为 _wa,后面主要是用于输出判断信息,会显示出来给人看,用法和格式化输出一致,如 quitf(_wa,"Answer is wrong, except %d, but read %d",ans,p);
quitp(score,..) 用来判 “部分正确”,第一个参数用来传入一个 \([0,1]\) 的实数,表示得分百分比,后面就一样了
testlib 程序会在读入格式错误,或者文件未被读完的时候报出 wrong output format 错误,为了避免这个错误,你也可以使用 while(!ouf.seekEof()) ouf.readToken() 来读完剩下的内容

                
            
        
浙公网安备 33010602011771号