mathmaker
0.6(alpha)
|
00001 # -*- coding: utf-8 -*- 00002 00003 # Mathmaker creates automatically maths exercises sheets 00004 # with their answers 00005 # Copyright 2006-2014 Nicolas Hainaux <nico_h@users.sourceforge.net> 00006 00007 # This file is part of Mathmaker. 00008 00009 # Mathmaker is free software; you can redistribute it and/or modify 00010 # it under the terms of the GNU General Public License as published by 00011 # the Free Software Foundation; either version 3 of the License, or 00012 # any later version. 00013 00014 # Mathmaker is distributed in the hope that it will be useful, 00015 # but WITHOUT ANY WARRANTY; without even the implied warranty of 00016 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 00017 # GNU General Public License for more details. 00018 00019 # You should have received a copy of the GNU General Public License 00020 # along with Mathmaker; if not, write to the Free Software 00021 # Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA 00022 00023 from lib import * 00024 from X_Structure import X_Structure 00025 import question 00026 #from core import * 00027 from core.calculus import * 00028 from lib.common import alphabet 00029 00030 # Here the list of available values for the parameter x_kind='' and the 00031 # matching self.x_subkind values 00032 # Note : the bypass value allows to give the value of *x_subkind* directly to 00033 # the matching question Constructor, bypassing the action of the present class 00034 AVAILABLE_X_KIND_VALUES = \ 00035 {'short_test' : ['medium_level', 'hard_level'], 00036 'mini_test' : ['two_factorizations'], 00037 'preformatted' : ['level_01_easy', 'level_02_easy', 00038 'level_02_intermediate', 'level_03_sum_squares', 00039 'level_03_difference_squares', 00040 'level_03_squares_differences', 00041 'level_03_some_not_factorizable', 00042 'level_03_all_kinds'], 00043 'bypass' : ['level_01'] 00044 } 00045 00046 X_LAYOUT_UNIT = "cm" 00047 ALT_DEFAULT_LAYOUT = { 'exc' : [ None, 'all' 00048 ], 00049 'ans' : [ [2, 9, 9], (1, 1, 00050 1, 1), 00051 None, 1 00052 ] 00053 } 00054 # ---------------------- lines_nb col_widths questions 00055 X_LAYOUTS = {'default' : 00056 { 'exc' : [ None, 'all' 00057 ], 00058 'ans' : [ [1, 6, 6, 6], (1, 1, 1) 00059 ] 00060 }, 00061 00062 ('short_test', 'hard_level') : 00063 { 'exc' : [ None, 'all' 00064 ], 00065 'ans' : [ [4, 9, 9], (1, 1, 00066 1, 1, 00067 1, 1, 00068 1, 1) 00069 ] 00070 }, 00071 00072 ('mini_test', 'two_factorizations') : 00073 { 'exc' : [ None, 'all' 00074 ], 00075 'ans' : [ None, 'all' 00076 ] 00077 }, 00078 00079 ('preformatted', 'level_01_easy') : 00080 { 'exc' : [ None, 'all' 00081 ], 00082 'ans' : [ ['?', 6, 6, 6], 'all' 00083 ] 00084 }, 00085 00086 ('preformatted', 'level_02_easy') : ALT_DEFAULT_LAYOUT, 00087 00088 ('preformatted', 'level_02_intermediate') : ALT_DEFAULT_LAYOUT, 00089 00090 ('preformatted', 'level_03_some_not_factorizable') : 00091 { 'exc' : [ None, 'all' 00092 ], 00093 'ans' : [ ['?', 6, 6, 6], 'all' 00094 ] 00095 }, 00096 00097 ('bypass', 'level_01') : 00098 { 'exc' : [ None, 'all' 00099 ], 00100 'ans' : [ ['?', 9,9], 'all' 00101 ] 00102 } 00103 00104 00105 } 00106 00107 # ------------------------------------------------------------------------------ 00108 # -------------------------------------------------------------------------- 00109 # ------------------------------------------------------------------------------ 00110 ## 00111 # @class X_Factorization 00112 # @brief Factorization exercises. 00113 class X_Factorization(X_Structure): 00114 00115 00116 00117 00118 00119 # -------------------------------------------------------------------------- 00120 ## 00121 # @brief Constructor. 00122 # @param embedded_machine The machine that will be used to write output. 00123 # @param **options Options detailed below : 00124 # - start_number=<integer> 00125 # (should be >= 1) 00126 # - number_of_questions=<integer> 00127 # /!\ only useful if you use x_kind and not preformatted 00128 # (should be >= 1) 00129 # - x_kind=<string> 00130 # ... 00131 # ... 00132 # - preformatted=<string> 00133 # /!\ preformatted is useless with short_test 00134 # /!\ number_of_questions is useless with preformatted 00135 # /!\ if you use it with the x_kind option, ensure there's a 00136 # preformatted possibility with this option 00137 # 'yes' 00138 # 'OK' 00139 # any other value will be understood as 'no' 00140 # - short_test=<string> 00141 # /!\ the x_kind option above can't be used along this option 00142 # use subtype if you need to make different short_test exercises 00143 # 'yes' 00144 # 'OK' 00145 # any other value will be understood as 'no' 00146 # - subtype=<string> 00147 # ... 00148 # ... 00149 # @todo Complete the description of the possible options ! 00150 # @return One instance of exercise.Factorization 00151 def __init__(self, embedded_machine, x_kind='default_nothing', **options): 00152 self.derived = True 00153 X_Structure.__init__(self, embedded_machine, 00154 x_kind, AVAILABLE_X_KIND_VALUES, X_LAYOUTS, 00155 X_LAYOUT_UNIT, **options) 00156 # The purpose of this next line is to get the possibly modified 00157 # value of **options 00158 options = self.options 00159 00160 # BEGINING OF THE ZONE TO REWRITE ------------------------------------- 00161 00162 default_question = question.Q_Factorization 00163 00164 # TEXTS OF THE EXERCISE 00165 self.text = {'exc' : _("Factorise : "), 00166 'ans' : "" 00167 } 00168 00169 # alternate texts section 00170 if self.x_kind == 'level_02_easy' \ 00171 or self.x_kind == 'level_02_intermediate': 00172 self.text = {'exc' : _("Factorise :"), 00173 'ans' : "" 00174 } 00175 00176 elif self.x_kind == 'level_03_some_not_factorizable' \ 00177 or (self.x_kind == 'mini_test' \ 00178 and self.x_subkind == 'two_factorizations'): 00179 #___ 00180 self.text = {'exc' : _("Factorise, if possible :"), 00181 'ans' : "" 00182 } 00183 00184 # SHORT TEST & OTHER PREFORMATTED EXERCISES 00185 if self.x_kind == 'short_test': 00186 if self.x_subkind == 'easy_level': 00187 # NOTE : the algebra (easy) short test uses directly one 00188 # question and passes its arguments (x_kind...) directly 00189 # to question.Factorization() (see below, at the end) 00190 pass 00191 00192 elif self.x_subkind == 'medium_level': 00193 lil_box = [] 00194 00195 lil_box.append(default_question( 00196 self.machine, 00197 q_kind='level_01', 00198 q_subkind='ax² + bx', 00199 expression_number=0)) 00200 00201 if randomly.heads_or_tails(): 00202 lil_box.append(default_question( 00203 self.machine, 00204 q_kind='level_01', 00205 q_subkind='ax² + b', 00206 expression_number=0)) 00207 else: 00208 lil_box.append(default_question( 00209 self.machine, 00210 q_kind='level_01', 00211 q_subkind='ax + b', 00212 expression_number=0)) 00213 00214 lil_box.append(default_question( 00215 self.machine, 00216 q_kind='level_01', 00217 q_subkind='not_factorizable', 00218 expression_number=0)) 00219 00220 for i in range(len(lil_box)): 00221 q = randomly.pop(lil_box) 00222 q.expression.set_name(alphabet.UPPERCASE[i]) 00223 for expression in q.steps: 00224 expression.set_name(alphabet.UPPERCASE[i]) 00225 self.questions_list.append(q) 00226 00227 elif self.x_subkind == 'hard_level': 00228 lil_box = [] 00229 00230 l03_kinds = ['sum_square_mixed', 00231 'difference_square_mixed', 00232 randomly.pop( 00233 ['squares_difference', 00234 'squares_difference_mixed' 00235 ]), 00236 randomly.pop( 00237 ['fake_01', 00238 'fake_01_mixed', 00239 'fake_02', 00240 'fake_02_mixed', 00241 'fake_03', 00242 'fake_03_mixed' 00243 ]), 00244 'fake_04_any_mixed' 00245 ] 00246 00247 00248 for n in range(len(l03_kinds)): 00249 lil_box.append(default_question( 00250 self.machine, 00251 q_kind='level_03', 00252 q_subkind=l03_kinds[n], 00253 expression_number=n+1)) 00254 00255 00256 l02_kinds = [('type_2_A1', 'no'), 00257 ('type_2_A0', 'yes'), 00258 ('type_4_A0', 'no')] 00259 00260 for n in range(len(l02_kinds)): 00261 lil_box.append(default_question( 00262 self.machine, 00263 q_kind='level_02', 00264 q_subkind=l02_kinds[n][0], 00265 max_coeff=10, 00266 minus_sign=l02_kinds[n][1], 00267 expression_number=n+len(l03_kinds)+1) 00268 ) 00269 00270 for i in range(len(lil_box)): 00271 q = randomly.pop(lil_box) 00272 q.expression.set_name(alphabet.UPPERCASE[i]) 00273 for expression in q.steps: 00274 if isinstance(expression, Expression): 00275 expression.set_name(alphabet.UPPERCASE[i]) 00276 self.questions_list.append(q) 00277 00278 elif self.x_kind == 'mini_test': 00279 if self.x_subkind == 'two_factorizations': 00280 lil_box = [] 00281 00282 lil_box.append(default_question(self.machine, 00283 q_kind='level_03', 00284 q_subkind=randomly.pop(['any_fake', 00285 'any_true'], 00286 weighted_table=[0.2, 00287 0.8] 00288 ), 00289 expression_number=1)) 00290 00291 l02_kinds = [('type_2_A1', 'no'), 00292 ('type_2_A0', 'yes'), 00293 ('type_4_A0', 'no')] 00294 00295 n = randomly.pop([0, 1, 2]) 00296 00297 lil_box.append(default_question( 00298 self.machine, 00299 q_kind='level_02', 00300 q_subkind=l02_kinds[n][0], 00301 max_coeff=10, 00302 minus_sign=l02_kinds[n][1], 00303 expression_number=2) 00304 ) 00305 00306 for i in range(len(lil_box)): 00307 q = randomly.pop(lil_box) 00308 q.expression.set_name(\ 00309 alphabet.UPPERCASE[i + self.start_number]) 00310 for expression in q.steps: 00311 if isinstance(expression, Expression): 00312 expression.set_name(\ 00313 alphabet.UPPERCASE[i + self.start_number]) 00314 self.questions_list.append(q) 00315 00316 00317 elif self.x_kind == 'preformatted': 00318 if self.x_subkind == 'level_01_easy': 00319 # n is the number of questions still left to do 00320 n = 10 00321 lil_box = [] 00322 00323 lil_box.append(default_question( 00324 self.machine, 00325 q_kind='level_01', 00326 q_subkind='ax² + bx', 00327 expression_number=10-n)) 00328 00329 n -= 1 00330 00331 if randomly.heads_or_tails(): 00332 lil_box.append(default_question( 00333 self.machine, 00334 q_kind='level_01', 00335 q_subkind='ax² + bx', 00336 expression_number=10-n)) 00337 00338 n -= 1 00339 00340 lil_box.append(default_question( 00341 self.machine, 00342 q_kind='level_01', 00343 q_subkind='ax² + b', 00344 expression_number=10-n)) 00345 00346 n -= 1 00347 00348 if randomly.heads_or_tails(): 00349 lil_box.append(default_question( 00350 self.machine, 00351 q_kind='level_01', 00352 q_subkind='ax² + b', 00353 expression_number=10-n)) 00354 00355 n -= 1 00356 00357 if randomly.heads_or_tails(): 00358 lil_box.append(default_question( 00359 self.machine, 00360 q_kind='level_01', 00361 q_subkind='ax² + b', 00362 expression_number=10-n)) 00363 00364 n -= 1 00365 00366 for i in range(n): 00367 lil_box.append(default_question( 00368 self.machine, 00369 q_kind='level_01', 00370 q_subkind='ax + b', 00371 expression_number=n-i) 00372 ) 00373 00374 for i in range(len(lil_box)): 00375 q = randomly.pop(lil_box) 00376 q.expression.set_name(alphabet.UPPERCASE[i]) 00377 for expression in q.steps: 00378 expression.set_name(alphabet.UPPERCASE[i]) 00379 self.questions_list.append(q) 00380 00381 00382 00383 elif self.x_subkind == 'level_02_easy': 00384 subkinds = ['type_1_A0', 00385 'type_1_D0', 00386 'type_1_G0'] 00387 00388 n1 = len(subkinds) 00389 00390 for i in range(n1): 00391 self.questions_list.append(default_question( 00392 self.machine, 00393 q_kind='level_02', 00394 q_subkind=randomly.pop(subkinds), 00395 minus_sign='no', 00396 expression_number=i) 00397 ) 00398 00399 subkinds = ['type_2_A0', 00400 'type_2_D0'] 00401 00402 n2 = len(subkinds) 00403 00404 for i in range(n2): 00405 self.questions_list.append(default_question( 00406 self.machine, 00407 q_kind='level_02', 00408 q_subkind=randomly.pop(subkinds), 00409 minus_sign='no', 00410 expression_number=i+n1) 00411 ) 00412 00413 elif self.x_subkind == 'level_02_intermediate': 00414 subkinds = ['type_1_D', 00415 'type_1_G0', 00416 'type_1_1'] 00417 00418 n1 = len(subkinds) 00419 00420 for i in range(n1): 00421 self.questions_list.append(default_question( 00422 self.machine, 00423 q_kind='level_02', 00424 q_subkind=randomly.pop(subkinds), 00425 minus_sign='no', 00426 expression_number=i) 00427 ) 00428 00429 subkinds = randomly.pop([['type_2_A0', 'type_2_D1'], 00430 ['type_2_A1', 'type_2_D0']]) 00431 00432 n2 = len(subkinds) 00433 00434 for i in range(n2): 00435 self.questions_list.append(default_question( 00436 self.machine, 00437 q_kind='level_02', 00438 q_subkind=randomly.pop(subkinds), 00439 minus_sign='no', 00440 expression_number=i+n1) 00441 ) 00442 00443 elif self.x_subkind == 'level_03_sum_squares': 00444 lil_box = [] 00445 00446 for n in range(2): 00447 lil_box.append(default_question( 00448 self.machine, 00449 q_kind='level_03', 00450 q_subkind='sum_square', 00451 expression_number=n+1)) 00452 00453 lil_box.append(default_question( 00454 self.machine, 00455 q_kind='level_03', 00456 q_subkind='sum_square_mixed', 00457 expression_number=n+1)) 00458 00459 for i in range(len(lil_box)): 00460 q = lil_box[i] 00461 q.expression.set_name(alphabet.UPPERCASE[i]) 00462 for expression in q.steps: 00463 if isinstance(expression, Expression): 00464 expression.set_name(alphabet.UPPERCASE[i]) 00465 self.questions_list.append(q) 00466 00467 elif self.x_subkind == 'level_03_difference_squares': 00468 lil_box = [] 00469 00470 for n in range(2): 00471 lil_box.append(default_question( 00472 self.machine, 00473 q_kind='level_03', 00474 q_subkind='difference_square', 00475 expression_number=n+1)) 00476 00477 lil_box.append(default_question( 00478 self.machine, 00479 q_kind='level_03', 00480 subkind ='difference_square_mixed', 00481 expression_number=n+1)) 00482 00483 for i in range(len(lil_box)): 00484 q = lil_box[i] 00485 q.expression.set_name(alphabet.UPPERCASE[i]) 00486 for expression in q.steps: 00487 if isinstance(expression, Expression): 00488 expression.set_name(alphabet.UPPERCASE[i]) 00489 self.questions_list.append(q) 00490 00491 00492 00493 elif self.x_subkind == 'level_03_squares_differences': 00494 lil_box = [] 00495 00496 for n in range(2): 00497 lil_box.append(default_question( 00498 self.machine, 00499 q_kind='level_03', 00500 q_subkind='squares_difference', 00501 expression_number=n+1)) 00502 00503 lil_box.append(default_question( 00504 self.machine, 00505 q_kind='level_03', 00506 q_subkind='squares_difference_mixed', 00507 expression_number=n+1)) 00508 00509 for i in range(len(lil_box)): 00510 q = lil_box[i] 00511 q.expression.set_name(alphabet.UPPERCASE[i]) 00512 for expression in q.steps: 00513 if isinstance(expression, Expression): 00514 expression.set_name(alphabet.UPPERCASE[i]) 00515 self.questions_list.append(q) 00516 00517 00518 00519 elif self.x_subkind == 'level_03_some_not_factorizable': 00520 lil_box = [] 00521 00522 q1 = default_question(self.machine, 00523 q_kind='level_03', 00524 q_subkind='any_true_mixed', 00525 expression_number=1) 00526 00527 q2 = default_question(self.machine, 00528 q_kind='level_03', 00529 q_subkind='any_fake_straight', 00530 expression_number=2) 00531 00532 q1q2 = [q1, q2] 00533 00534 lil_box.append(randomly.pop(q1q2)) 00535 lil_box.append(randomly.pop(q1q2)) 00536 00537 for n in range(3): 00538 lil_box.append(default_question(self.machine, 00539 q_kind='level_03', 00540 q_subkind='any_true', 00541 expression_number=n+3)) 00542 00543 for n in range(2): 00544 lil_box.append(default_question(self.machine, 00545 q_kind='level_03', 00546 q_subkind='any_fake', 00547 expression_number=n+5)) 00548 00549 for n in range(2): 00550 lil_box.append(default_question(self.machine, 00551 q_kind='level_03', 00552 q_subkind='any', 00553 expression_number=n+7)) 00554 00555 00556 00557 for i in range(len(lil_box)): 00558 q = lil_box[i] 00559 q.expression.set_name(alphabet.UPPERCASE[i]) 00560 for expression in q.steps: 00561 if isinstance(expression, Expression): 00562 expression.set_name(alphabet.UPPERCASE[i]) 00563 self.questions_list.append(q) 00564 00565 00566 00567 elif self.x_subkind == 'level_03_all_kinds': 00568 all_kinds = ['sum_square', 00569 'sum_square_mixed', 00570 'difference_square', 00571 'difference_square_mixed', 00572 'squares_difference', 00573 'squares_difference_mixed', 00574 'fake_01', 00575 'fake_01_mixed', 00576 'fake_02', 00577 'fake_02_mixed', 00578 'fake_03', 00579 'fake_03_mixed', 00580 'fake_04_A', 00581 'fake_04_A_mixed', 00582 'fake_04_B', 00583 'fake_04_B_mixed', 00584 'fake_04_C', 00585 'fake_04_C_mixed', 00586 'fake_04_D', 00587 'fake_04_D_mixed' 00588 ] 00589 00590 lil_box = [] 00591 00592 for n in range(len(all_kinds)): 00593 lil_box.append(default_question( 00594 self.machine, 00595 q_kind='level_03', 00596 q_subkind=all_kinds[n], 00597 expression_number=n+1)) 00598 00599 for i in range(len(lil_box)): 00600 q = lil_box[i] 00601 q.expression.set_name(alphabet.UPPERCASE[i]) 00602 for expression in q.steps: 00603 if isinstance(expression, Expression): 00604 expression.set_name(alphabet.UPPERCASE[i]) 00605 self.questions_list.append(q) 00606 00607 00608 00609 # OTHER EXERCISES (BY_PASS OPTION) 00610 else: 00611 for i in range(self.q_nb): 00612 self.questions_list.append( 00613 default_question(self.machine, 00614 expression_number=i+self.start_number, 00615 q_kind = self.x_subkind, 00616 **options) 00617 ) 00618 00619 00620 # -------------------------------------------------------------------------- 00621 ## 00622 # @brief Writes the answers of the questions to the output. 00623 #def write_answer(self): 00624 # M = self.machine 00625 # max_per_page = 12 00626 # i_count = 0 00627 # j = 0 00628 # tabular_format = [3, "p{6 cm} p{6 cm} p{6 cm}"] 00629 00630 # if 'short_test' in self.options \ 00631 # and (self.options['short_test'] == 'hard_level'): 00632 # #___ 00633 # tabular_format = [2, "p{9 cm} p{9 cm}"] 00634 00635 # M.write_tabular_begins(tabular_format[1]) 00636 # for i in xrange(len(self.questions_list)): 00637 # j += 1 00638 # i_count += 1 00639 # self.questions_list[i].write_answer() 00640 # if j < tabular_format[0]: 00641 # M.write_separator_tabular_columns() 00642 # if j == tabular_format[0] and i_count < max_per_page - 1: 00643 # M.write_separator_tabular_lines() 00644 # j = 0 00645 00646 # if i_count == max_per_page - 1: 00647 # i_count = 0 00648 # j = 0 00649 # M.write_tabular_ends() 00650 # M.write_tabular_begins(tabular_format[1]) 00651 #M.write_new_line() 00652 00653 # M.write_tabular_ends() 00654 00655 #M.write_new_line() 00656 00657 00658 00659 00660 00661 00662 # END OF THE ZONE TO REWRITE ------------------------------------------