Add files via upload

master
JesterHey 2 years ago committed by GitHub
parent 3c06e34ce9
commit b27f80cd1c
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23

@ -0,0 +1,30 @@
{
"50598": {
"describe": "本关任务:统计一个字符串中字符个数(不含空格)。\n可以使用充分利用字符串自带的函数进行操作以便简化程序的编写。",
"require": "根据提示,在右侧编辑器##########begin######和#######end######之间补全代码请不要在此区间使用print语句。不要修改区间外面的代码。",
"code": "# -*- coding: utf-8 -*-\n\"\"\"\nCreated on Mon Sep 7 15:23:19 2020\n\n@author: hyr\n拼接统计字数将空格改为换行查找子串\n\"\"\"\n\nsongs=input()#仅包含空格和中文\n\n\n##############begin###########\n#1. songs中存放的字符串仅包含空格和中文请统计字符串变量\nsongs中中文字的数量直接将统计结果输出\ncount = 0\nfor char in songs:\n if char != ' ':\n count+=1\nprint(count)\n\n\n\n\n#############end##############",
"verified": false,
"last_modified": "2023-12-05 15:44:02"
},
"50599": {
"describe": "本关任务:将字符串中的空格替换为换行。",
"require": "根据提示,在右侧编辑器##########begin#########和##########end##########之间补充代码请不要在该区间使用print语句。其他区域的语句不要改动。",
"code": "# -*- coding: utf-8 -*-\n\"\"\"\nCreated on Mon Sep 7 15:23:19 2020\n\n@author: hyr\n拼接统计字数将空格改为换行查找子串\n\"\"\"\n\nsongs=input()#歌曲歌词,仅包含空格和中文\ntitle=input()#歌曲标题\n\n\n\n##############begin###########\n#1. 将songs中的空格改为换行。注意首尾空格应去掉不用替换成\n换行符连续的空格仅替换为一个换行符\n\n\n\n\n\n#2. 将title作为歌曲的首行显示输出整首歌曲\n\n",
"verified": false,
"last_modified": "2023-12-05 15:44:06"
},
"50601": {
"describe": "本关任务:统计字符串中文字出现的次数。",
"require": "根据提示,在右侧编辑器############begin#########和###########end##########区间补充代码",
"code": "# -*- coding: utf-8 -*-\n\"\"\"\nCreated on Mon Sep 7 15:23:19 2020\n\n@author: hyr\n拼接统计字数将空格改为换行查找子串\n\"\"\"\n\nsongs=input()#仅包含空格和中文字\n\n\n\n################begin#############\n#1. 输出songs中出现最多的一个中文字并输出该字出现次数。\n#注意:如果有多个字出现次数相同,请以原文本中最先出现的那个\n为准。\n\n\n\n\n\n################end#############\n\n",
"verified": false,
"last_modified": "2023-12-05 15:44:10"
},
"50608": {
"describe": "本关任务:将歌曲以最长的那一行为标准,其它行居中对齐左补句号输出。\n例如\n。。。等风雨经过\n。。。等我们相见\n。。你微笑仰望着天\n。。我们一起种下心愿\n。。等花开等它实现\n该流的泪还是滑过你的脸\n。。我始终在你身边\n。。说好要一起走很远\n。。努力让未来鲜艳\n。在爱面前需要什么字眼\n。对你的承诺我一定实现\n真正的爱不需要有太多语言\n。有些感动就放在心里面\n。在爱面前需要什么字眼\n。付出的瞬间也就是永远\n每天离希望又再靠近了一点\n。守护家园是最美画面\n。。。我们为爱奉献\n。。。。为梦改变",
"require": "根据提示,在右侧编辑器##########begin##############和##########end#############区间补充代码。",
"code": "# -*- coding: utf-8 -*-\n\"\"\"\nCreated on Mon Sep 7 15:23:19 2020\n\n@author: hyr\n拼接统计字数将空格改为换行查找子串\n\"\"\"\n\nsongs=input()#仅含空格和中文的歌词字符串\n\n\n######begin################## \n#1. 将songs按空格分割成一个字符串列表\n#提示可用字符串的split函数\n\n\n\n\n\n#######end##################\n\n\n#############begin####################\n#2. 以上面的字符串列表为基础,找出最长的那一个字符串,以它为",
"verified": false,
"last_modified": "2023-12-05 15:44:14"
}
}

@ -1,13 +1,10 @@
'''
本模块用于定义云端读写的相关操作包括上传下载删除等
'''
import oss2 import oss2
import json
import shutil
import os import os
import get_answer import json
#获取本地json文件 # 云端存储的文件名称都是shixun_id.json,并且要保证都是有答案的.
def get_json(file):
return [i for i in os.listdir(file) if i.endswith('.json')]
#获取json文件名
json_name = get_json('./')[0]
# 阿里云 OSS 配置 # 阿里云 OSS 配置
access_key_id = 'LTAI5t927vdUFZa9NRnWfrL3' access_key_id = 'LTAI5t927vdUFZa9NRnWfrL3'
access_key_secret = 'FbXoJUqe545eZhWFvADvGcFwatsGAx' access_key_secret = 'FbXoJUqe545eZhWFvADvGcFwatsGAx'
@ -16,13 +13,23 @@ endpoint = 'oss-cn-shenzhen.aliyuncs.com'
# 创建Bucket对象所有Object相关的接口都可以通过Bucket对象来进行 # 创建Bucket对象所有Object相关的接口都可以通过Bucket对象来进行
bucket = oss2.Bucket(oss2.Auth(access_key_id, access_key_secret), endpoint, bucket_name) bucket = oss2.Bucket(oss2.Auth(access_key_id, access_key_secret), endpoint, bucket_name)
# 判断文件是否存在 # 判断文件是否存在
def is_exist(name): def is_exist(name:str) -> bool:
return bucket.object_exists(name) return bucket.object_exists(name)
exist = is_exist(json_name) # 如果文件存在则下载到本地并命名为shixun_id_answer
# 如果文件存在,则下载到本地并覆盖本地文件
def download(name): def download(name):
bucket.get_object_to_file(name, name) bucket.get_object_to_file(name, f'{name}_answer')
# 上传函数,用于获得答案后上传到云端,此步骤在获得答案后调用
# (to do)如果用户将答案认证为正确则将本地json中的verified参数改为True后再上传并覆盖云端文件
def upload(name): def upload(name):
# 上传前先检验文件中的每个键对应的值的answer键是否存在以及其对应的值是否为空如果为空则不上传
with open(name,'r',encoding='utf-8') as f:
data = json.load(f)
for i,j in data.items():
if 'answer' not in j.keys() or j['answer'] == '':
# 断言查询结果并抛出异常
assert False,'答案为空,不予上传'
bucket.put_object_from_file(name, name) bucket.put_object_from_file(name, name)
def delete(name):
bucket.delete_object(name)

@ -0,0 +1,19 @@
from openai import OpenAI
import openai
import os
openai.api_base = "https://api.openai-proxy.com"
openai.api_key = "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"
# os.environ['http_proxy'] = 'http://127.0.0.1:10809'
# os.environ['https_proxy'] = 'http://127.0.0.1:10809'
client = OpenAI(
api_key='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',
base_url='https://api.openai-proxy.com'
)
resp = client.chat.completions.create(
model='gpt-3.5-turbo',
messages=[
{'role': 'user', 'content': '你好!'}
]
)
print(resp.choices[0].message.content)

@ -45,14 +45,15 @@ promot = '现在我想让你扮演一个Python程序员来解一个问题
# 初始化异步客户端 # 初始化异步客户端
client = AsyncOpenAI( client = AsyncOpenAI(
api_key='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' api_key='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'
) )
def get_answer_from_api(jsonfile:dict,client:AsyncOpenAI,promot:str) -> dict: def get_answer_from_api(jsonfile:dict,client:AsyncOpenAI,promot:str) -> dict:
data = jsonfile data = jsonfile
client = client client = client
promot = promot promot = promot
# 异步函数来获取答案 # 异步函数来获取答案
async def get_answer(value): async def get_answer(key,value):
cid = key
des, req, code = value['describe'], value['require'], value['code'] des, req, code = value['describe'], value['require'], value['code']
question = f'问题描述:{des}\n任务需求:{req}\n根据上面的需求,你需要补充并完善代码:\n{code}' question = f'问题描述:{des}\n任务需求:{req}\n根据上面的需求,你需要补充并完善代码:\n{code}'
try: try:
@ -63,24 +64,25 @@ def get_answer_from_api(jsonfile:dict,client:AsyncOpenAI,promot:str) -> dict:
{'role': 'user', 'content': question} {'role': 'user', 'content': question}
] ]
) )
return response.choices[0].message.content return f'{cid}/{response.choices[0].message.content}'
except Exception as e: except Exception as e:
print(f'错误信息:{e}') print(f'错误信息:{e}')
# 主函数 # 主函数
async def main(data) -> dict: async def main(data) -> dict:
tasks = [get_answer(value) for value in list(data.values())[:1:]] ansewer_data = data
answers = await asyncio.gather(*tasks) tasks = [get_answer(cid,value) for cid,value in data.items()]
answers = await asyncio.gather(*tasks) # 返回一个列表,列表中的每个元素为每个异步任务的返回值
#由于异步获得的答案顺序不确定,需要处理,先把答案按照关卡id排序
answers.sort(key=lambda x:int(x.split('/')[0]))
# 在data的每个value中新增一个键值对键为answer值为答案并作为返回值返回 # 在data的每个value中新增一个键值对键为answer值为答案并作为返回值返回
for i,val in enumerate(data.values()): for i in range(len(answers)):
val['answer'] = answers[i] ansewer_data[list(ansewer_data.keys())[i]]['answer'] = answers[i]
return data return ansewer_data
# 运行主函数 # 运行主函数
#issue:由于异步获得的答案顺序不确定,需要处理
return asyncio.run(main(data=data)) return asyncio.run(main(data=data))
new_data = get_answer_from_api(jsonfile=data,client=client,promot=promot) new_data = get_answer_from_api(jsonfile=data,client=client,promot=promot)
print(new_data) print(new_data)

@ -10,7 +10,9 @@
''' '''
#导入所需模块 #导入所需模块
import os
import json import json
import time
from selenium.webdriver import Chrome from selenium.webdriver import Chrome
from selenium.webdriver.chrome.options import Options from selenium.webdriver.chrome.options import Options
from selenium.webdriver.common.by import By from selenium.webdriver.common.by import By
@ -19,10 +21,11 @@ import re
from lxml import etree from lxml import etree
import time import time
import requests import requests
from cloud import is_exist,download,upload from cloud import is_exist,download
#配置参数 #配置参数
opt = Options() opt = Options()
opt.add_experimental_option('detach', True) opt.add_experimental_option('detach', True)
opt.add_argument('--headless')
chrome_driver = 'D:\ChromeDownload\chromedriver-win64\chromedriver-win64' chrome_driver = 'D:\ChromeDownload\chromedriver-win64\chromedriver-win64'
#以下部分在发行版本需要优化UI #以下部分在发行版本需要优化UI
# url = input('请输入作业中任意一关的网址:') # url = input('请输入作业中任意一关的网址:')
@ -33,7 +36,7 @@ user_name = 'hnu202311020126'
password = 'hzy123456' password = 'hzy123456'
# 另外目前好像只有实训作业有这些参数其他的作业例如编程作业就没有所以先判断一下是否为实训作业可以通过用户输入的url判断 # 另外目前好像只有实训作业有这些参数其他的作业例如编程作业就没有所以先判断一下是否为实训作业可以通过用户输入的url判断
# 主要是看educoder.net/后面是否有tasks如果有则是实训作业否则不是实训作业 # 主要是看educoder.net/后面是否有tasks如果有则是实训作业否则不是实训作业
def is_practice(url): def is_practice(url:str) -> bool:
obj=re.compile(r'www.educoder.net/tasks') obj=re.compile(r'www.educoder.net/tasks')
if obj.search(url): if obj.search(url):
return True return True
@ -41,7 +44,7 @@ def is_practice(url):
return False return False
if is_practice(url): if is_practice(url):
#构造selenium对象 #构造selenium对象
safari = Chrome() safari = Chrome(options=opt)
safari.get(url) safari.get(url)
#模拟登录 #模拟登录
safari.implicitly_wait(10) safari.implicitly_wait(10)
@ -65,14 +68,24 @@ if is_practice(url):
response = requests.get(url=id_url, headers=headers) response = requests.get(url=id_url, headers=headers)
shixun_id = dict(response.json())['challenge']['shixun_id'] shixun_id = dict(response.json())['challenge']['shixun_id']
#判断云端文件是否存在 #判断云端文件是否存在
try:
exist = is_exist(f'{shixun_id}.json') exist = is_exist(f'{shixun_id}.json')
if exist: #存在,则跳转到云端下载并终止本程序 if exist: #存在,则跳转到云端下载并终止本程序
print('云端文件已存在,正在下载') print('云端文件已存在,正在下载')
download(f'{shixun_id}.json') download(f'{shixun_id}.json')
safari.close() # 检测本地文件是否下载完成
while True:
try:
if os.path.exists(f'{shixun_id}.json'):
print('下载完成')
safari.quit()
exit() exit()
else: #不存在,则继续执行本程序 break
print('云端文件不存在,开始获取参数') except Exception as e:
print(e)
except Exception as e:
print(e)
finally: #不存在,则继续执行本程序
#获取关卡数 #获取关卡数
#点击展开关卡页面 #点击展开关卡页面
safari.find_element(By.XPATH,'//*[@id="task-left-panel"]/div[1]/a[1]').click() safari.find_element(By.XPATH,'//*[@id="task-left-panel"]/div[1]/a[1]').click()
@ -92,15 +105,8 @@ if is_practice(url):
''' '''
obj1 = re.compile(r'<h3 id="任务描述">任务描述</h3><p>(?P<describe>.*?)</p>',re.S) obj1 = re.compile(r'<h3 id="任务描述">任务描述</h3><p>(?P<describe>.*?)</p>',re.S)
obj2 = re.compile(r'<h3 id="编程要求">编程要求</h3><p>(?P<require>.*?)</p>',re.S) obj2 = re.compile(r'<h3 id="编程要求">编程要求</h3><p>(?P<require>.*?)</p>',re.S)
#初始化一个总的json文件名称为课程的id #初始化一个字典,用于存放所有关卡的参数
total = {} total = {}
#另外,目前好像只有实训作业有这些参数,其他的作业例如编程作业就没有,所以先判断一下是否为实训作业
# def is_practice():
# try:
# safari.find_element(By.XPATH,'//*[@id="task-left-panel"]/div[1]/a[1]')
# return True
# except BaseException:
# return False
i=1 i=1
try: try:
while i <= task_num: while i <= task_num:
@ -139,17 +145,27 @@ if is_practice(url):
'describe':describe[0] if len(describe) != 0 else '', 'describe':describe[0] if len(describe) != 0 else '',
'require':require[0] if len(require) != 0 else '', 'require':require[0] if len(require) != 0 else '',
'code':code, 'code':code,
'verified': False #这个参数是用来标记答案是否被用户认证为正确答案的初始值为False 'verified': False, #这个参数是用来标记答案是否被用户认证为正确答案的初始值为False
'last_modified': time.strftime('%Y-%m-%d %H:%M:%S',time.localtime(time.time())) #这个参数是用来标记答案最后一次被修改的时间,初始值为当前时间
} }
#把每一关的参数存入总的字典中 #把每一关的参数存入总的字典中
total[challenge_id] = task total[challenge_id] = task
#去往下一关 #去往下一关
i += 1 i += 1
except BaseException: except BaseException:
print('获取参数失败') print(f'{challenge_id}参数获取参数失败')
#判断爬取到的代码是否存在空值,如果存在空值,则重新爬取
for value in total.values():
if value['code'] == '':
print('检测到代码参数为空值,重新爬取')
safari.close()
os.system('python get_params.py')
exit()
#把参数写入本地json文件中文件名字与shixun_name相同键为course_id值为一个列表列表中每个元素为一个字典字典中包含每一关的参数 #把参数写入本地json文件中文件名字与shixun_name相同键为course_id值为一个列表列表中每个元素为一个字典字典中包含每一关的参数
with open(f'{shixun_id}.json','w',encoding='utf-8') as f: with open(f'{shixun_id}.json','w',encoding='utf-8') as f:
json.dump(total,f,ensure_ascii=False,indent=4) json.dump(total,f,ensure_ascii=False,indent=4)
#关闭浏览器
safari.quit()
else: else:
print('这不是一个实训作业') print('这不是一个实训作业')
exit() exit()

Loading…
Cancel
Save