上市公司年报格式准则–说明
上市公司每年皆应发布上一年度年报,且须符合证监会制定之格式准则。严格来说,上市公司年报格式准则全称为—《公开发行证券的公司信息披露内容与格式准则第2号—年度报告的内容与格式》。证监会对年报格式准则,会不断地进行修订。近些年进行了四次修订:
 
 提取不同修订版目录准则代码
为了了解不同修订版的要求,我用如下Python代码,提取了关于年报目录准则。
import os
import re
import fitz # pip install pymupdf
import csv
filenames = os.listdir()
prefix = '公开发行证券的公司信息披露内容与格式准则第2号'
# 须点击上面列表中链接,下载四个修订版本PDF文件,
# 并放置在该代码文件所在文件夹。
# 筛选出格式准则文件
pdf = [f for f in filenames if f.startswith(prefix) and f.endswith('.pdf')]
# 提取修订年份
year = [f[-12:-5] for f in pdf]
# 提取PDF文本,因有一份无法被pdfplumber库提取,故采用pymupdf
def getText(pdf):
    text = ''
    doc = fitz.open(pdf)
    for page in doc:
        text += page.getText()
    doc.close()
    return(text)
# 主要部分
def getTOC(pdf):
    text = getText(pdf)
    p1 = re.compile('第二章\s*年度报告正文(.*)第三章\s*年度报告摘要',re.DOTALL)
    subtext = p1.search(text).group(0)
    p = re.compile('(?<=\\n)(第\w{1,2}节)\s+(.*)(?=\\n)')
    listOftuple = p.findall(subtext)
    return(listOftuple)
# text_list = [getText(f) for f in pdf]
toc = [getTOC(f) for f in pdf]
# 存储至 '.csv' 文件,方便后续使用。
def to_csv(year,toc):
    with open(year+'.csv', mode='w', newline='', encoding='utf-8') as f:
        writer = csv.writer(f)
        for t in toc:
            writer.writerow([t[0],t[1]])
    return
for i in range(len(year)):
    to_csv(year[i], toc[i])
 
 目录准则 对比表
| 第一节 | 重要提示、目录和释义 | 重要提示、目录和释义 | 重要提示、目录和释义 | 重要提示、目录和释义 | 
| 第二节 | 公司简介 | 公司简介和主要财务指标 | 公司简介和主要财务指标 | 公司简介和主要财务指标 | 
| 第三节 | 会计数据和财务指标摘要 | 公司业务概要 | 公司业务概要 | 管理层讨论与分析 | 
| 第四节 | 董事会报告 | 经营情况讨论与分析 | 经营情况讨论与分析 | 公司治理 | 
| 第五节 | 重要事项 | 重要事项 | 重要事项 | 环境和社会责任 | 
| 第六节 | 股份变动及股东情况 | 股份变动及股东情况 | 股份变动及股东情况 | 重要事项 | 
| 第七节 | 董事、监事、高级管理人员和员工情况 | 优先股相关情况 | 优先股相关情况 | 股份变动及股东情况 | 
| 第八节 | 公司治理 | 董事、监事、高级管理人员和员工情况 | 董事、监事、高级管理人员和员工情况 | 优先股相关情况 | 
| 第九节 | 内部控制 | 公司治理 | 公司治理 | 债券相关情况 | 
| 第十节 | 财务报告 | 公司债券相关情况 | 公司债券相关情况 | 财务报告 | 
| 第十一节 |  | 财务报告 | 财务报告 |  | 
| 第十二节 |  | 备查文件目录 | 备查文件目录 |  | 
 
 目录准则 各修订表
 2021年—目录准则
| 第一节 | 重要提示、目录和释义 | 
| 第二节 | 公司简介和主要财务指标 | 
| 第三节 | 管理层讨论与分析 | 
| 第四节 | 公司治理 | 
| 第五节 | 环境和社会责任 | 
| 第六节 | 重要事项 | 
| 第七节 | 股份变动及股东情况 | 
| 第八节 | 优先股相关情况 | 
| 第九节 | 债券相关情况 | 
| 第十节 | 财务报告 | 
 
 2017年—目录准则
| 第一节 | 重要提示、目录和释义 | 
| 第二节 | 公司简介和主要财务指标 | 
| 第三节 | 公司业务概要 | 
| 第四节 | 经营情况讨论与分析 | 
| 第五节 | 重要事项 | 
| 第六节 | 股份变动及股东情况 | 
| 第七节 | 优先股相关情况 | 
| 第八节 | 董事、监事、高级管理人员和员工情况 | 
| 第九节 | 公司治理 | 
| 第十节 | 公司债券相关情况 | 
| 第十一节 | 财务报告 | 
| 第十二节 | 备查文件目录 | 
 
 2016年—目录准则
| 第一节 | 重要提示、目录和释义 | 
| 第二节 | 公司简介和主要财务指标 | 
| 第三节 | 公司业务概要 | 
| 第四节 | 经营情况讨论与分析 | 
| 第五节 | 重要事项 | 
| 第六节 | 股份变动及股东情况 | 
| 第七节 | 优先股相关情况 | 
| 第八节 | 董事、监事、高级管理人员和员工情况 | 
| 第九节 | 公司治理 | 
| 第十节 | 公司债券相关情况 | 
| 第十一节 | 财务报告 | 
| 第十二节 | 备查文件目录 | 
 
 2012年—目录准则
| 第一节 | 重要提示、目录和释义 | 
| 第二节 | 公司简介 | 
| 第三节 | 会计数据和财务指标摘要 | 
| 第四节 | 董事会报告 | 
| 第五节 | 重要事项 | 
| 第六节 | 股份变动及股东情况 | 
| 第七节 | 董事、监事、高级管理人员和员工情况 | 
| 第八节 | 公司治理 | 
| 第九节 | 内部控制 | 
| 第十节 | 财务报告 | 
 
 
 第二次作业提示
 html 模板
html模板: homework2_output_template.html
<!DOCTYPE html>
<html lang="en" dir="ltr">
  <head>
    <meta charset="utf-8">
    <title></title>
    <style media="screen">
      h3 {
        text-align: center;
        margin-top: 50px;
      }
      p {
        margin-top: 20px;
        margin-bottom: 20px;
        margin:auto;
        max-width: 500px;
      }
    </style>
  </head>
  <body>
      %s
  </body>
</html>
 
 示例代码
import os
import re
import fitz # pip install pymupdf
import csv
filenames = os.listdir()
prefix = '公开发行证券的公司信息披露内容与格式准则第2号'
# 须点击上面列表中链接,下载四个修订版本PDF文件,
# 并放置在该代码文件所在文件夹。
# 筛选出格式准则文件
pdf = [f for f in filenames if f.startswith(prefix) and f.endswith('.pdf')]
# 提取修订年份
year = [f[-12:-5] for f in pdf]
# 提取PDF文本,因有一份无法被pdfplumber库提取,故采用pymupdf
def getText(pdf):
    text = ''
    doc = fitz.open(pdf)
    for page in doc:
        text += page.getText()
    doc.close()
    return(text)
def getSubtext(pdf):
    text = getText(pdf)
    p1 = re.compile('第二章\s*年度报告正文(.*)第三章\s*年度报告摘要',
                    re.DOTALL)
    subtext = p1.search(text).group(0)
    return(subtext)
# 主要部分
def getTOC(pdf):
    subtext = getSubtext(pdf)
    p = re.compile('(?<=\\n)(第\w{1,2}节)\s+(.*)(?=\\n)')
    listOftuple = p.findall(subtext)
    return(listOftuple)
# text_list = [getText(f) for f in pdf]
toc = [getTOC(f) for f in pdf]
def getTOC_content(pdf):
    subtext = getSubtext(pdf)
    p = re.compile('(?<=\\n)(第\w{1,2}节)\s+(.*)(?=\\n)')
    index = []
    for match in p.finditer(subtext):
        s = match.start()
        e = match.end()
        index.append((s,e))
    #
    content = []
    for i in range(len(index)-1):
        s = index[i][1]
        e = index[i+1][0]
        content.append(subtext[s:e])
    last_start = index[-1][1]
    last_end = subtext.rfind('\n第三章')
    content.append(subtext[last_start:last_end])
    return((index,content))
# index, content = getTOC_content(pdf[0])
list_of_content = [getTOC_content(f) for f in pdf]
def export_to_html(pdf,toc,content):
    f = open('homework2_output_template.html', encoding='utf-8')
    html = f.read()
    f.close()
    template = '<div><h3>%s</h3><p>%s</p></div>'
    toc_list = [t[0]+' '+ t[1] for t in toc]
    div = [template % (t,c) for (t,c) in zip(toc_list, content)]
    div = ''.join(div)
    html = html % div
    f = open('homework2_%s.html' % pdf, 'w',encoding='utf-8')
    f.write(html)
    f.close()
    return()
content_list = [c[1] for c in list_of_content]
export_to_html(pdf[0], toc[0], content_list[0])