码迷,mamicode.com
首页 > 其他好文 > 详细

[从头学数学] 第222节 带着计算机去高考(十四)

时间:2016-05-27 12:10:28      阅读:234      评论:0      收藏:0      [点我收藏+]

标签:

剧情提要:
[机器小伟]在[工程师阿伟]的陪同下进入了[九转金丹]之第八转的修炼。设想一个场景:
如果允许你带一台不连网的计算机去参加高考,你会放弃选择一个手拿计算器和草稿本吗
?阿伟决定和小伟来尝试一下用计算机算高考题会是怎样的感觉。

正剧开始:

星历2016年05月25日 17:14:22, 银河系厄尔斯星球中华帝国江南行省。
[工程师阿伟]正在和[机器小伟]一起做着2013年的江苏省数学高考题]。


上面这句话确实在本文而言是名不符实的,因为这张卷子阿伟和[机器小伟]

谁也没做,纯粹贴题了。


粗略看了一下,难度还是5.5环,也就是属于很难的那个行列。试想你每次

为了取得一件宝物都不得不受到5.5次调戏的那种感觉吧,就是这样。


技术分享


技术分享


技术分享


技术分享


技术分享


技术分享


技术分享


技术分享


技术分享


技术分享


技术分享


技术分享


技术分享


技术分享


技术分享


技术分享


技术分享


技术分享


技术分享


技术分享


技术分享


技术分享


技术分享


技术分享


技术分享


技术分享


技术分享


当年阿伟从来没敢交过白卷,现在胆也肥了,也敢交白卷了,真是非常潇洒的感觉。


这次呢,阿伟和[机器小伟]主要在研究怎样解二元二次方程组,先看这个测试题吧:


技术分享



技术分享


这两条曲线就是这么个图:


技术分享


之所以能解二元二次方程组,是因为它们系数之中满足这样的关系:


技术分享


<span style="font-size:18px;">>>> 
['(0)', '(2)*b_[1]^[1]*b_[2]^[1]', '(0)', '(4)*c_[1]^[1]', '(4)*c_[2]^[1]']
['(4)*b_[1]^[2]*b_[2]^[2]', '(-16)*b_[1]^[2]*c_[2]^[1]', '(-16)*b_[2]^[2]*c_[1]^[1]', '(64)*c_[1]^[1]*c_[2]^[1]']
['(0)', '(0)', '(0)', '(0)', '(4)*b_[1]^[2]*b_[2]^[2]', '(16)*b_[1]^[1]*b_[2]^[1]*c_[1]^[1]', '(16)*b_[1]^[1]*b_[2]^[1]*c_[2]^[1]', '(16)*c_[1]^[2]', '(32)*c_[1]^[1]*c_[2]^[1]', '(16)*c_[2]^[2]']
['(0)', '(0)', '(16)*b_[1]^[1]*b_[2]^[1]*c_[1]^[1]', '(16)*b_[1]^[1]*b_[2]^[1]*c_[2]^[1]', '(16)*c_[1]^[2]', '(-32)*c_[1]^[1]*c_[2]^[1]', '(16)*c_[2]^[2]', '(16)*b_[1]^[2]*c_[2]^[1]', '(16)*b_[2]^[2]*c_[1]^[1]']

#测试,二元二次方程组的根的恒等式,已消去一元
#先要保证两个方程的消去的那个元的最高次项系数为1
def tmp3():
    part1 = alg.strformat(['b_[1]', 'b_[2]']);
    part2 = alg.strformat(['b_[1]^[2]', '-4c_[1]']);
    part3 = alg.strformat(['b_[2]^[2]', '-4c_[2]']);

    part4 = alg.strpow_n(part1, 2);
    part5 = alg.stradd(part2, part3);
    part6= alg.strcombine(alg.stradd(part4, alg.minus(part5)));
    #print(part6);

    part7 = alg.strdot(alg.strdot(['(4)'], part2), part3);
    part7 = alg.strcombine(part7);
    #print(part7);

    part8 = alg.strpow_n(part6, 2);
    part8 = alg.strcombine(part8);
    #print(part8);

    result = alg.strcombine(alg.stradd(part8, alg.minus(part7)));
    print(result);
	
>>> 
['(0.0)', '(0.0)', '(1.0)*b_[1]^[1]*b_[2]^[1]*c_[1]^[1]', '(1.0)*b_[1]^[1]*b_[2]^[1]*c_[2]^[1]', '(1.0)*c_[1]^[2]', '(-2.0)*c_[1]^[1]*c_[2]^[1]', '(1.0)*c_[2]^[2]', '(1.0)*b_[1]^[2]*c_[2]^[1]', '(1.0)*b_[2]^[2]*c_[1]^[1]']</span>

<span style="font-size:18px;">		var s = [
			'在a_[1] == a_[2] == 1时',
			'((b_[1]-b_[2])^[2]-(b_[1]^[2]-4c_[1]+b_[2]^[2]-4c_[2]))^[2]',
			'== 4(b_[1]^[2]-4c_[1])(b_[2]^[2]-4c_[2])',
			' ',
			'这个恒等式可以化为:',
			'(1)*b_[1]*b_[2]*c_[1]+(1)*b_[1]*b_[2]*c_[2]', 
			'+(1)*c_[1]^[2]-(2)*c_[1]*c_[2]+(1)*c_[2]^[2]', 
			'+(1)*b_[1]^[2]*c_[2]+(1)*b_[2]^[2]*c_[1]',
			' = 0'
			
			
		];</span>


再给工具中新添两个方法:

<span style="font-size:18px;">   #把一个只包括+号的多项式字符串拆分成多项式数组
    #如'(1)*x^[2]+(-1)' => ['(1)*x^[2]', '(-1)']
    def str2Array(self, str1):
        array = [];
        #加号位置
        signIndex = str1.find('+');
        print(signIndex);

        start = 0;
        count = 0;
        while (signIndex != '-1' and count < 10):
            #符合要求的必须连着下一个单项式的系数
            #按照统一格式是左括号开始
            if str1[signIndex+1] == '(':
                array.append(str1[start:signIndex]);
                start = signIndex + 1;

            signIndex = str1.find('+', signIndex+1);
            if (signIndex == -1):
                break;

        array.append(str1[start:]);

        return array;
		
>>> 
9
['(1)*x^[2]', '(-1)']

    #解二元二次方程组
    def solveEquationExp2(self, array1, array2):
        #输入的是两个系数矩阵
        #矩阵具有这样的形式:[['1'], [b_[1]], [c_[1]]]
        #也就是对于ax^[2]+bx+c=0来说, a=1, 而b, c是带参数多项式数组
        #注意,系数是数组,不是字符串等。
        a_1, b_1, c_1 = array1[0], array1[1], array1[2];
        a_2, b_2, c_2 = array2[0], array2[1], array2[2];

        #恒等式
        '''
        [
        '(1.0)*b_[1]^[1]*b_[2]^[1]*c_[1]^[1]',
        '(1.0)*b_[1]^[1]*b_[2]^[1]*c_[2]^[1]',
        '(1.0)*c_[1]^[2]',
        '(-2.0)*c_[1]^[1]*c_[2]^[1]',
        '(1.0)*c_[2]^[2]',
        '(1.0)*b_[1]^[2]*c_[2]^[1]',
        '(1.0)*b_[2]^[2]*c_[1]^[1]'] = 0
        '''
        #这些运算都是针对数组的
        b1b2 = alg.strcombine(alg.strdot(b_1, b_2));
        c1c2 = alg.strcombine(alg.strdot(c_1, c_2));
        c12 = alg.strcombine(alg.strpow_n(c_1, 2));
        c22 = alg.strcombine(alg.strpow_n(c_2, 2));
        b12 = alg.strcombine(alg.strpow_n(b_1, 2));
        b22 = alg.strcombine(alg.strpow_n(b_2, 2));
        
        part1 = alg.strcombine(alg.strdot(b1b2, alg.stradd(c_1, c_2)));
        part2 = alg.strcombine(c12+alg.strdot(['(-2)'], c1c2)+c22);
        part3 = alg.strcombine(alg.stradd(alg.strdot(b12, c_2),
                                          alg.strdot(b22, c_1)));
        result = alg.strcombine(part1+part2+part3);
        return result;
</span>


这样就可以进行套路化的解题了:


<span style="font-size:18px;">>>> 
step1:  ['(1)*x^[2]', '(1)*y^[2]', '(2)*x*y', '(-1)']
step2:  ['(1)', '(2)*x', '(1)*x^[2]+(-1)']
step1:  ['(1)*x^[2]', '(4)*y^[2]', '(-1)']
step2:  ['(4)', '0', '(1)*x^[2]+(-1)']
step3:  ['(1)'] ['(2)*x'] ['(1)*x^[2]', '(-1)']
step3:  ['(4)'] ['0'] ['(1)*x^[2]', '(-1)']
step4:  ['(0)', '(4)*x^[4]', '(-4)*x^[2]']
step5:  [4, 0, -4, 0, 0]
step6:  [ 1. -1.  0.  0.]
step7:  ['(((-((2)*x)))+(((((2)*x)^[2])+((-4)*(((1))*((1)*x^[2]+(-1)))))^[0.5]))/((2)*((1)))', '(((-((2)*x)))-(((((2)*x)^[2])+((-4)*(((1))*((1)*x^[2]+(-1)))))^[0.5]))/((2)*((1)))']
step8:  [[1.0, 0.0], [1.0, -2.0], [0.0, 1.0], [0.0, -1.0], [0.0, 1.0], [0.0, -1.0]]

#测试
def tmp2():
    solve = StringAlgSolve();

    f = alg.strformat(['x^[2]', 'y^[2]', '2xy', '-1']);
    print('step1: ', f);

    poly_y_f = solve.coefArray(f, 'y');
    print('step2: ', poly_y_f);

    #以y为参数的二次多项式的系数,消元是消y
    a1, b1, c1 = poly_y_f[0], poly_y_f[1], poly_y_f[2];

    g = alg.strformat(['x^[2]', '4y^[2]', '-1']);
    print('step1: ', g);

    poly_y_g = solve.coefArray(g, 'y');
    print('step2: ', poly_y_g);

    #以y为参数的二次多项式的系数,消元是消y
    a2, b2, c2 = poly_y_g[0], poly_y_g[1], poly_y_g[2];

    
    a1, b1, c1 =solve.str2Array(a1), solve.str2Array(b1),solve.str2Array(c1)
    a2, b2, c2 =solve.str2Array(a2), solve.str2Array(b2),solve.str2Array(c2)

    print('step3: ', a1, b1, c1);
    print('step3: ', a2, b2, c2);
    poly_x = solve.solveEquationExp2([a1, b1, c1], [a2, b2, c2]);
    print('step4: ', poly_x);

    poly_x = solve.coefPoly(poly_x, 'x');
    print('step5: ', poly_x);

    #求得x的根
    roots = np.roots(poly_x);
    print('step6: ', roots);

    #求方程式<1>的y关于x的表达式
    expr_y_root = solve.solvePoly(poly_y_f);
    print('step7: ', expr_y_root);
    expr_y_root2 = solve.solvePoly(poly_y_g);
    print('step7: ', expr_y_root2);

    
    #求相交点的坐标对组
    points = [];
    points2 = [];
    for i in range(len(roots)):
        real = abs(roots[i].real);
        abs_ = abs(roots[i]);
        #实数根
        if abs(real-abs_) < 0.001:
            
            for j in range(len(expr_y_root)):
                x = roots[i];
                y = solve.strEval(expr_y_root[j], 'x', x);
                points.append([x, y]);
                y = solve.strEval(expr_y_root2[j], 'x', x);
                points2.append([x, y]);
    print('step8: ', points);
    print('step8: ', points2);

    #比较两组点,得出交点[1, 0], [-1, 0]</span>


解答到此结束,下面是一些过程产物,可忽略。


<span style="font-size:18px;">	if (1) {      
        var r = 20;            
        config.setSector(1,1,1,1);              
        config.graphPaper2D(0, 0, r);            
        config.axis2D(0, 0,180);              
                
        //坐标轴设定        
        var scaleX = 2*r, scaleY = 2*r;          
        var spaceX = 0.4, spaceY = 0.4;           
        var xS = -10, xE = 10;          
        var yS = -10, yE = 10;          
        config.axisSpacing(xS, xE, spaceX, scaleX, 'X');            
        config.axisSpacing(yS, yE, spaceY, scaleY, 'Y');            
                    
        var transform = new Transform();            
        //存放函数图像上的点        
        var a = [], b = [], c = [], d = [];          
                  
        //需要显示的函数说明    
                    //希腊字母表(存此用于Ctrl C/V  
            //ΑΒΓΔΕΖΗΘΙΚΛΜΝΞΟΠΡΣΤΥΦΧΨΩ  
            //αβγδεζηθικλμνξοπρστυφχψω  
        var f1 = 'x+y = 1', f2 = 'x+y=-1', f3 = 'x^[2]+4y^[2] = 1', f4 = '';        
            
  
        //函数描点    
        //参数方程  
        var x, y;  
        var pointA = [];  
          
        for (var thita = 0; thita < Math.PI*2; thita +=Math.PI/48) {  
			x = Math.cos(thita);
			a.push([x, 1-x]);
			b.push([x, -1-x]);
            c.push([Math.cos(thita), 0.5*Math.sin(thita)]);  
			
        }  
          
                  
        //存放临时数组        
        var tmp = [];        
                  
        //显示变换        
        if (a.length > 0) {        
            a = transform.scale(transform.translate(a, 0, 0), scaleX/spaceX, scaleY/spaceY);         
            //函数1        
            tmp = [].concat(a);            
            shape.pointDraw(tmp, 'red');            
            tmp = [].concat(a);            
            shape.multiLineDraw(tmp, 'pink');          
                      
            plot.setFillStyle('red');        
            plot.fillText(f1, 100, -90, 200);          
        } 

		//显示变换        
        if (b.length > 0) {        
            b = transform.scale(transform.translate(b, 0, 0), scaleX/spaceX, scaleY/spaceY);         
            //函数1        
            tmp = [].concat(b);            
            shape.pointDraw(tmp, 'red');            
            tmp = [].concat(b);            
            shape.multiLineDraw(tmp, 'green');          
                      
            plot.setFillStyle('green');        
            plot.fillText(f2, 100, -120, 200);          
        }  
	
		//显示变换        
        if (c.length > 0) {        
            c = transform.scale(transform.translate(c, 0, 0), scaleX/spaceX, scaleY/spaceY);         
            //函数1        
            tmp = [].concat(c);            
            shape.pointDraw(tmp, 'blue');            
            tmp = [].concat(c);            
            shape.multiLineDraw(tmp, '#0088FF');          
                      
            plot.setFillStyle('blue');        
            plot.fillText(f3, 100, -150, 200);          
        }  
          
    }
	</span>


<span style="font-size:18px;">	//测试
	if (1) {
		var mathText = new MathText();
		
		//希腊字母表(存此用于Ctrl C/V
			//ΑΒΓΔΕΖΗ ΘΙΚΛΜΝΞ ΟΠΡ ΣΤΥ ΦΧΨ Ω
			//αβγδεζη θικλμνξ οπρ στυ φχψ ω
			
		//希腊大小写字母
		var Gc = 'ΑΒΓΔΕΖΗΘΙΚΛΜΝΞΟΠΡΣΤΥΦΧΨΩ';
		var Gs = 'αβγδεζηθικλμνξοπρστυφχψω';
		
		
		
		var s = [
			/*
			'测试题:求交点',
			'x^[2]+2xy+y^[2]=1 _[(1)]',
			'x^[2]+4y^[2] = 1  _[(2)]',
			' ',
			'step1: 两曲线的多项式',
			'step2: 消去y元',
			'step3: 将两组二次系数导入方程恒等式',
			'step4: 得到方程恒等式,这是关于元x的四次恒等式,不含根号',
			'step5: 导出恒等式的系数阵列。',*/
			
			'step6: 解恒等式的根,有四个根。',
			'step7: 求得曲线方程中y元关于x元的根的代数式。',
			'step8: 把代数式求值,得到交点坐标'
			
			
			
		];</span>


从此以后,[机器小伟]就可以纵横圆锥曲线了。

留个快照吧:

技术分享


现在阿伟真的很爽,觉得外边的风景也漂亮起来了。


本节到此结束,欲知后事如何,请看下回分解。


注:本节中的解法虽然没错,但最后结果却是错的,原因出在那个恒等式不够强大,

由于时间不够,虽然阿伟意识到解错了,也没办法,在下一节中会给出正确的解法

以及结果,大家可以去查看。当然,知道这样解是得不出正确结果,也是一种收获。



[从头学数学] 第222节 带着计算机去高考(十四)

标签:

原文地址:http://blog.csdn.net/mwsister/article/details/51499995

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!