ScoreAnalysisController.class.php
8.74 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
<?php
/**
* 【考试中心-后台】试卷考试成绩人数分布接口
* ScoreAnalysisController.class.php
* @author : wanghuan
* @date : 2017-07-17
* @version: $Id$
*/
namespace Apicp\Controller\Answer;
use Common\Common\User;
use Common\Common\Department;
use Common\Service\PaperService;
use Common\Service\RightService;
use Common\Service\AnswerService;
class ScoreAnalysisController extends AbstractController
{
// 最大区间数
const AVGNUM_MAX = 10;
// 最小区间数
const AVGNUM_MIN = 9;
/** @var PaperService */
protected $paper_serv;
/** @var RightService */
protected $right_serv;
/** @var AnswerService */
protected $answer_serv;
public function before_action($action = '')
{
if (!parent::before_action($action)) {
return false;
}
// 初始化User
$this->user = User::instance();
// 实例化试卷service
$this->paper_serv = new PaperService();
// 实例化权限service
$this->right_serv = new RightService();
// 实例化答卷service
$this->answer_serv = new AnswerService();
return true;
}
public function Index_post()
{
// 接收post参数
$params = I('post.');
// 参数为空,返回提示"参数不能为空"
if (empty($params)) {
E('_ERR_PARAMS_NOT_NULL');
}
// 试卷id
$ep_id = intval($params['ep_id']);
// 试卷id为空,返回提示"试卷ID不能为空"
if (!$ep_id) {
E('_EMPTY_EP_ID');
}
// 根据试卷id获取试卷详情
$paper = $this->paper_serv->get($ep_id);
// 试卷不存在
if (empty($paper)) {
E('_ERR_PAPER_NOT_FOUND');
}
// 查询条件初始化
$answer_conds = [
'ep_id' => $ep_id,
'answer_status' => AnswerService::READ_OVER, // 已批阅
];
// 【部门】
if (isset($params['dpIds']) && !empty($params['dpIds']) && is_array($params['dpIds'])) {
$params_dpids = $params['dpIds'];
$dpServ = &Department::instance();
// 取子级部门ID
$child_ids = $dpServ->list_childrens_by_cdid($params_dpids);
// 合并部门ID
$dp_ids = array_merge($params_dpids, array_values($child_ids));
$dp_conds = [
'dpIdList' => $dp_ids
];
$dp_users = $this->user->listAll($dp_conds);
// 选择部门下的员工id集合
$d_uids = array_column($dp_users, 'memUid');
// 组装查询条件
$dp_uids = $this->answer_serv->get_uids($paper['ep_id'], $d_uids);
if (!empty($dp_uids)) {
$answer_conds['uid'] = $dp_uids;
} else {
// 空查询所有 为了避免查询所有传入0
$answer_conds['uid'] = [0];
}
}
// 总分
$score_total = 0;
// 部门下考试的员工考试信息
$join = [];
// 试卷类型
$paper_type = $paper['paper_type'];
// 分页
$page_option = null;
// 排序
$order_by = [];
// 查询字段
$fields = 'ea_id,uid,my_score,created';
// 模拟考试
if (PaperService::SIMULATION_PAPER_TYPE == $paper_type) {
// 部门下模拟考试的员工考试信息
$join = $this->answer_serv->get_mock_join_list($answer_conds, $page_option, $order_by, $fields);
if (!empty($join)) {
// 取考分列
$my_max_score = array_column($join, 'my_max_score');
// 考分之和
$score_total = array_sum($my_max_score);
}
} elseif (PaperService::EVALUATION_PAPER_TYPE == $paper_type) { // 测评考试
// 只用最高分进行计算
$answer_conds['is_score_top'] = AnswerService::IS_SCORE_TOP_TRUE;
// 部门测评考试通过的员工考试信息
$join = $this->answer_serv->list_by_conds($answer_conds, $page_option, $order_by, $fields);
if (!empty($join)) {
// 取考分列
$my_score = array_column($join, 'my_score');
// 考分之和
$score_total = array_sum($my_score);
}
}
$data_x = [];
$data_y = [];
// 平均分初始化
$average = 0;
if (!empty($join)) {
// 试卷总分
$total_score = intval($paper['total_score']);
// 试卷总分小于10
if ($total_score < self::AVGNUM_MAX) {
// x轴数据:分数区段
$data_x = $this->numberAvg($total_score, $total_score);
} else {
// 余数
$remainder = $total_score % self::AVGNUM_MAX;
// 余数不为空
if ($remainder) {
// 不能整除,除以9,余数放到第10份
$data_x = $this->numberAvg($total_score, self::AVGNUM_MIN);
} else {
// 能够整除分10份
$data_x = $this->numberAvg($total_score, self::AVGNUM_MAX);
}
}
// y轴数据:人数
$data_y = $this->getListData($data_x, $join, $paper_type);
// 平均分
$average = round(($score_total / count($join)), 2);
}
// 返回结果
$this->_result = [
'average' => $average,
'data_x' => $data_x,
'data_y' => $data_y
];
}
/**
* 组装返回的x轴、y轴数据
*
* @param $data_x array 成绩区间段
* @param $join array 部门下有权限考试的员工的考试信息
* @param $paper_type int 试卷类型:0=测评考试,1=模拟考试
*
* @return array 返回y轴数据
*/
protected function getListData($data_x, $join, $paper_type)
{
// 模拟考试
if (PaperService::SIMULATION_PAPER_TYPE == $paper_type) {
$score_col = array_column($join, 'my_max_score');
} elseif (PaperService::EVALUATION_PAPER_TYPE == $paper_type) { // 测评考试
$score_col = array_column($join, 'my_score');
}
// 初始化返回数据
$data_y = [];
// 初始为与data_x等长的数组
$data_y = array_pad($data_y, count($data_x), 0);
$score_col = array_unique($score_col);
// 组装返回数据
foreach ($score_col as $score) {
// 模拟考试
if (PaperService::SIMULATION_PAPER_TYPE == $paper_type) {
$score_list = $this->answer_serv->seekarr($join, 'my_max_score', $score);
} elseif (PaperService::EVALUATION_PAPER_TYPE == $paper_type) { // 测评考试
$score_list = $this->answer_serv->seekarr($join, 'my_score', $score);
}
// 分数为0,归为第一个分区
if (0 == $score) {
$data_y[0] = $data_y[0] + count($score_list);
} else {
// 循环判断是否在分数区段内
foreach ($data_x as $key => $val) {
// 分隔分区分数
$score_arr = explode('-', $val);
// 分数在区段内,进行统计
if ($score > $score_arr[0] && $score <= $score_arr[1]) {
$data_y[$key] = $data_y[$key] + count($score_list);
}
}
}
}
return $data_y;
}
/**
* 将一个数值划分为n个区段
*
* @param $number int 划分的数值(整数)
* @param $avgNumber int 份数
*
* @return array 区段数组
*/
protected function numberAvg($number, $avgNumber)
{
// 初始化
$array = [];
// 待划分数值为0,
if ($number == 0) {
// 返回份数长度值为0的数组
$array = array_fill(0, $avgNumber, 0);
} else {
// 平均值整数部分
$avg = floor($number / $avgNumber);
// 余数
$remainder = $number % $avgNumber;
// 分段最大值
$ceilSum = $avg * $avgNumber;
$k = 0;
for ($i = 0; $i < $avgNumber; $i++) {
$str = $k . '-' . ($k + $avg);
array_push($array, $str);
$k = $k + $avg;
}
// 有余数
if ($remainder) {
$key = array_pop(array_keys($array)) + 1;
$value = $ceilSum . '-' . $number;
$array[$key] = strval($value);
}
}
return $array;
}
}