提交 22337ad3 编写于 作者: 幻灰龙's avatar 幻灰龙

Merge branch 'rfc002' into 'master'

add rfc 002

See merge request !1
# 习题和相关工具
技能树习题使用 markdown 定义。工具脚本会根据习题的结构生成对应的元信息。
## 习题的格式
习题是一个 markdown 文本,当前仅支持单选题,习题文本需要描述题干、习题答案、选项。对于设计为生成 notebook 的习题,还可以携带用于填充
notebook 的模板或 aop 章节。
### 题干
一个典型的习题结构如下:
````markdown
# Hello World
以下 `Hello World` 程序中,能够正确输出内容的是:
## 答案
```java
public class App {
public static void main(String[] args){
System.out.println("Hello World");
}
}
```
## 选项
### A
```java
public class App {
public int main(){
System.out.printf("Hello World");
return 0;
}
}
```
### B
```java
public class App {
public static void main(String[] args){
println("Hello World");
}
}
```
### C
```java
import stdout
public class App {
public int main(){
print("Hello World\n");
return 0;
}
}
```
````
这个习题文件分为几个部分。
首先是一级标题,这个标题会出现在最终的习题页面。作为题目的标题。
然后是习题的描述,习题的描述可以有多段,除了文本,也可以是有序号或无序号的列表,也可以是代码段等合法的 markdown 格式。
目前题干不支持内部的子结构,这是出于简化设计的考虑。与下面介绍的习题章节结构设计有关。
### 习题的答案
习题答案是一个二级标题为 `答案` 的章节
```markdown
## 答案
答案内容
```
这个内容应紧跟着习题描述,在这之前可能有可选的模板或 aop 定义,但是不会再有其它内容,关于用来生成notebook的模板或aop结构,我们放在后面讨论。
答案的标题一定是 `答案`,这个二级标题不会出现在问题页。如果习题没有包含答案,后续处理时会报错。
### 习题的选项
在答案只有,应该有一个二级标题,名为 `选项` ,它列举了除正确答案之外的所有被选项。后续的技能树服务会在生成习题页面时,随机选择三个选项,与答案
一起展示给用户。因此,至少需要三个备选项。选项章节的形态如下:
````markdown
## 选项
### 带有代码段的选项
```java
,,,
```
### 文本选项
这段内容会成为问题页面上的选项
### 文本选项
选项也可以包含多个段落
````
原则上,我们鼓励尽可能多的选项,给学习者提供更好的体验。每个选项的三级标题不会出现在题目页,我们可以利用它叙述一些简短的信息。
### 习题代码和 notebook
每个习题的markdown文件,对应一个同名的json文件,例如 `hello.md` ,仓库的维护者会通过工具脚本或钩子生成一个对应的 `hello.json`
它的内容如下:
```json
{
"type": "code_options",
"author": "ccat",
"source": "hello.md",
"notebook_enable": false,
"exercise_id": "ee4d10ae488b4900835e52d184822962"
}
```
这些配置信息可以由程序自动生成,但是有时可能我们需要做一些调整。例如当我们设置 `notebook_enable``true` 时,技能树服务会为其生成对应的
notebook 页,这些 notebook 页可以为学习者提供可执行的程序环境。
目前 CSDN 的 notebook 服务支持 c、python、java 三种语言,对于一些程序示例,特别是 C 或 Java 代码,可能整个可执行代码放进题目中过于冗长,
因此我们允许将题目中的代码嵌入到预先定义的模板中,组合成完整的可执行代码,再组装成 notebook 单元。而这些代码不需要出现在题目页。
为此我们支持两种代码包装形式:模板或 AOP 。
如果我们在题干之后,答案之前,插入一个名为 `template` 的章节,那么它的正文中定义的代码会当作模板处理:
````markdown
## template
```c
#inlcude <stdio.h>
int main(int argc, char** argv){
$code
}
```
````
组装 notebook 页时,$code 占位符会被替换成 `答案` 中的代码段。这个占位符形式遵循 python 标准库 `string.Template` 类型的模板语法。
一些代码示例,可能需要更复杂的代码"外壳",把它分成在 `code` 之前和之后两部分更合适,此时我们可以使用 `aop` 章节。
````markdown
## aop
### before
```java
package app;
public class Main{
public static void main(String[] argv){
```
### after
```java
System.out.println("hello");
}
}
```
````
章节标题 aop 来自 Java 的`面向方面编程(AOP)`。这里的三级标题 before 和 after 如果存在,它们的正文内容会在组装 notebook 页时出现在答案
的前面和后面。
AOP 章节可以只包含 before 和 after 中的某一个,并不需要两部分都齐全。
AOP 或模板章节,需要放在题干之后,答案之前。未来可能会调整位置,允许写到习题文本的最后。
\ No newline at end of file
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册