结对编程--四则运算(Java)萧英杰 夏浚杰

结对编程--四则运算(Java)萧英杰 夏浚杰

Github项目地址

功能要求

题目:实现一个自动生成小学四则运算题目的命令行程序

  1. 使用 -n 参数控制生成题目的个数(实现)
  2. 使用 -r 参数控制题目中数值(自然数、真分数和真分数分母)的范围,该参数可以设置为1或其他自然数。该参数必须给定,否则程序报错并给出帮助信息(实现)
  3. 生成的题目中计算过程不能产生负数,也就是说算术表达式中如果存在形如e1 − e2的子表达式,那么e1 ≥ e2 (实现)
  4. 生成的题目中如果存在形如e1 ÷ e2的子表达式,那么其结果应是真分数 (实现)
  5. 每道题目中出现的运算符个数不超过3个 (实现)
  6. 程序一次运行生成的题目不能重复,即任何两道题目不能通过有限次交换+和×左右的算术表达式变换为同一道题目。例如,23 + 45 = 和45 + 23 = 是重复的题目,6 × 8 = 和8 × 6 = 也是重复的题目。3+(2+1)和1+2+3这两个题目是重复的,由于+是左结合的,1+2+3等价于(1+2)+3,也就是3+(1+2),也就是3+(2+1)。但是1+2+3和3+2+1是不重复的两道题,因为1+2+3等价于(1+2)+3,而3+2+1等价于(3+2)+1,它们之间不能通过有限次交换变成同一个题目。生成的题目存入执行程序的当前目录下的Exercises.txt文件 (实现)
  7. 在生成题目的同时,计算出所有题目的答案,并存入执行程序的当前目录下的Answers.txt文件 (实现)
  8. 程序应能支持一万道题目的生成 (实现)
  9. 程序支持对给定的题目文件和答案文件,判定答案中的对错并进行数量统计,统计结果输出到文件Grade.txt (实现)

PSP

PSP2.1Personal Software Process Stages预估耗时(分钟)实际耗时(分钟)
Planning计划6090
· Estimate· 估计这个任务需要多少时间6090
Development开发19202270
· Analysis· 需求分析 (包括学习新技术)200250
· Design Spec· 生成设计文档5060
· Design Review· 设计复审 (和同事审核设计文档)2020
· Coding Standard· 代码规范 (为目前的开发制定合适的规范)1010
· Design· 具体设计3040
· Coding· 具体编码15001800
· Code Review· 代码复审5030
· Test· 测试(自我测试,修改代码,提交修改)6060
Reporting报告100100
· Test Report· 测试报告6060
· Size Measurement· 计算工作量1010
· Postmortem & Process Improvement Plan· 事后总结, 并提出过程改进计划3030
合计20802460

效能分析

编码过程中,在表达式生成和查重方面花费了很多时间,对于查重,需要将已经生成的表达式加入到一个集合里,原本想用数组存放查重表达式,后来发现此方案效率偏低,之后在网上查找了一些资料后,采用HashMap存放,使用containsKey()进行查重。经过测试,该方案优于原方案。此外,还对代码进行了一定程度上的优化,使代码更加简洁,效率提高。

设计实现过程

1.操作数的生成

题目要求生成的操作数可以是自然数、分数,由于整数可以看成分母为1的分数,所以将整数化作分数进行计算。因此设计了一个分数类用于分数的定义,存放,计算和输出。

2.表达式的生成和计算

经过查询资料和讨论之后,我们决定用fraction_create方法和operator_create方法随机生成几个操作数和运算符,将它们按规则组成表达式。至于表达式的计算,生成的表达式是中缀表达式,我们将它转换为后缀表达式,并calculate方法计算,得出答案。
1483675-20180930144944346-811981987.png

代码说明

Fraction类:分数的的定义,存放,计算和输出
package myapp;

public class Fraction {
    //分子
    private int a;
    //分母
    private int b;
     
     //分数
     public Fraction(int a, int b) {
         this.a = a;
            if (b == 0) {
                throw new ArithmeticException("分母不能为零");
            } else {
                this.b = b;
            }
            simple();
     }
     
    
    //化简
     private Fraction simple() {
            int gcd = this.gcd(this.a, this.b);
            this.a /= gcd;
            this.b /= gcd;
            return this;
     }
     
     //最大公约数
     private int gcd(int a, int b) {
            int mod = a % b;
            if (mod == 0) {
                return b;
            } else {
                return gcd(b, mod);
            }
        }

     //四则运算
        public Fraction add(Fraction second) {//加法
            return new Fraction(this.a * second.b + second.a * this.b,
                    this.b * second.b);
        }

        public Fraction sub(Fraction second) {//减法
            return new Fraction(this.a * second.b - second.a * this.b,
                    this.b * second.b);
        }

        public Fraction mult(Fraction second) {//乘法
            return new Fraction(this.a*second.a,
                    this.b * second.b);
        }

        public Fraction div(Fraction second) {//除法
            return new Fraction(this.a*second.b,
                    this.b * second.a);
        }
        
        
        //分数类转字符串类型
        public String toString() {
            if (this.b==1) {
                return String.valueOf(a);
            }
            else if(this.a>this.b) {
                int c=0;
                c=this.a/this.b;
                this.a=this.a%this.b;
                return String.valueOf(c)+"'"+String.valueOf(a)+"/"+String.valueOf(b);
            } 
            else{
            return String.valueOf(a)+"/"+String.valueOf(b);}
        }
        
        public static Fraction tofraction(String str) {
            str=str.replaceAll(" ", "");
            int a=1;
            int b=1;
            int s1=str.indexOf("'");
            int s2=str.indexOf("/");
            if(s1!=-1) {
                int c=Integer.valueOf(str.substring(0,s1));
                b=Integer.valueOf(str.substring(s2+1));
                a=c*b+Integer.valueOf(str.substring(s1+1,s2));
            } else if(s2!=-1) {
                b=Integer.valueOf(str.substring(s2+1));
                a=Integer.valueOf(str.substring(0,s2));
            } else {
                a=Integer.valueOf(str);
                b=1;
            }
            return new Fraction(a,b);
        }
    
        //比较大小,比较此分数是否大于输入分数
        public boolean isgreaterthan2(Fraction f) {
            int z=this.a * f.b - f.a * this.b;
            if(z>0) {return true;}
            else return false;
        }
        public boolean isZero() {
            return a == 0;
        }
        
}
Expression类:表达式的生成
package myapp;

import java.util.Random;

public class Expression {
    Random random=new Random();
    Calc c=new Calc();
    
    //随机生成一个分数
    public Fraction fraction_create(int r) {
        int choose=random.nextInt(2)+1;
        int denominator=1;
        int numerator=0;

        if(choose==1) { //整数
            numerator=random.nextInt(r);
            denominator=1;      
        }else {
        denominator=random.nextInt(r)+1;
        numerator=random.nextInt(r*r+1);
        while(numerator/denominator>=r) {
            denominator=random.nextInt(r)+1;
            numerator=random.nextInt(r+1);}     
        }
        return new Fraction( numerator , denominator ); 
    }
    
    //随机生成运算符
    public char operator_create() {
        int oper=random.nextInt(4);    
        char sign;
        switch (oper) {
        case 0:
            sign='+';           
            break;
        case 1:
            sign='-';
            break;
        case 2:
            sign='×';
            break;
        case 3:
            sign='÷';
            break;
        default:
            sign='+';
        }
        return sign;
    }

    //生成表达式
    public String getexp(int r) {
        String expression="";
         int ran=random.nextInt(3);
         switch (ran) {
         case 0:
             expression=oneopexp(r);
             break;
         case 1:
             expression=twoopexp(r);
             break;
         case 2:
             expression=threeopexp(r);
             break;
         }
         return expression;
    }
    
    //一个运算符
    public String oneopexp(int r) {
        Fraction f1=fraction_create(r);
        Fraction f2=fraction_create(r); 
        char op=operator_create();
        String exp ="";
        switch (op) {
        case '+':
            exp= f1+" + "+f2;
            break;
        case '-':
            if(!f1.isgreaterthan2(f2)) {
            Fraction temp;
            temp=f1;f1=f2;f2=temp;
            }
            exp= f1+" - "+f2;
            break;
        case '×':
            exp= f1+" × "+f2;
            break;
        case '÷':
            while(f2.isZero()) {
                f2=fraction_create(r);
            }
            exp= f1+" ÷ "+f2;
            break;
        }
        return exp;
    }
    
    //两个运算符
    public String twoopexp(int r){
        Fraction f1=fraction_create(r);
        Fraction f2=fraction_create(r);
        Fraction f3=fraction_create(r);
        
        char op1=operator_create();
        char op2=operator_create();
        String exp ="";
        String exp1="";
        switch (op1) {
        case '+':
            
            exp= f1+" + "+f2;
            break;
        case '-':
            if(!f1.isgreaterthan2(f2)) {
            Fraction temp;
            temp=f1;f1=f2;f2=temp;
            }
            
            exp= f1+" - "+f2;
            break;
        case '×':
            
            exp= f1+" × "+f2;
            break;
        case '÷':
            while(f2.isZero()) {
                f2=fraction_create(r);
            }
            
            exp= f1+" ÷ "+f2;
            break;
        }
        switch (op2) {
        case '+':
            
            exp1=exp+" + "+f3;
            break;
        case '-':
            if(!c.calculate(exp).isgreaterthan2(f3)) {  
                
            exp1= f3+" - "+"("+exp+")";
            }else {
                
            exp1= exp+" - "+f3;}
            break;
        case '×':
            
            exp1= "("+exp+")"+" × "+f3;
            break;
        case '÷':
            while(f3.isZero()) {
                f3=fraction_create(r);
            }
            
            exp1="("+exp+")"+" ÷ "+f3;
            break;
        }       
        
        return exp1;
    }
    
    //三个运算符改
        public String threeopexp(int r){
            Fraction f1=fraction_create(r);
            Fraction f2=fraction_create(r);
            Fraction f3=fraction_create(r);
            Fraction f4=fraction_create(r);

            char op1=operator_create();
            char op2=operator_create();
            char op3=operator_create();
            String exp ="";
            String exp1="";
            String exp2="";
            switch (op1) {
            case '+':
                
                exp= f1+" + "+f2;
                break;
            case '-':
                if(!f1.isgreaterthan2(f2)) {
                Fraction temp;
                temp=f1;f1=f2;f2=temp;
                }
                
                exp= f1+" - "+f2;
                break;
            case '×':
                
                exp= f1+" × "+f2;
                break;
            case '÷':
                while(f2.isZero()) {
                    f2=fraction_create(r);
                }
                
                exp= f1+" ÷ "+f2;
                break;
            }
            switch (op2) {
            case '+':
                
                exp1=exp+" + "+f3;
                break;
            case '-':
                if(!c.calculate(exp).isgreaterthan2(f3)) {
                    
                exp1= f3+" - "+"("+exp+")";
                }else {
                
                exp1= exp+" - "+f3;}
                break;
            case '×':
                
                exp1= "("+exp+")"+" × "+f3;
                break;
            case '÷':
                while(f3.isZero()) {
                    f3=fraction_create(r);
                }
                
                exp1="("+exp+")"+" ÷ "+f3;
                break;
            }   
            switch (op3) {
            case '+':
                
                exp2=exp1+" + "+f4;
                break;
            case '-':
                if(!c.calculate(exp1).isgreaterthan2(f4)) {
                    
                exp2= f4+" - "+"("+exp1+")";
                }else {
                    
                exp2= exp1+" - "+f4;}
                break;
            case '×':
                
                exp2= "("+exp1+")"+" × "+f4;
                break;
            case '÷':
                while(f4.isZero()) {
                    f4=fraction_create(r);
                }
                
                exp2="("+exp1+")"+" ÷ "+f4;
                break;
            }
            
            return exp2;
        }
}
Calc类:中缀表达式转后缀表达式并计算,查重表达式的生成
package myapp;

import java.util.ArrayList;
import java.util.List;
import java.util.Stack;

public class Calc {
    char[] oper6= {'+','-','×','÷','(',')'};
    String[] oper4={"+","-","×","÷"};
    private static int ADDITION=1;
    private static int SUBTRACTION=1;
    private static int MULTIPLICATION=2;
    private static int DIVISION=2;
    
    public static int getValue(String op){
        int value;
        switch (op){
            case "+":
                value=ADDITION;
                break;
            case "-":
                value=SUBTRACTION;
                break;
            case "×":
                value=MULTIPLICATION;
                break;
            case "÷":
                value=DIVISION;
                break;
            default:
                value=0;
        }
        return value;
    }
    
    
    //判断是否是操作符
    public boolean isoper(char c) {
        for(char op:oper6) {
            if(op==c) return true;
        }
        return false;
    }
    
    public boolean isoper(String s) {
        for(String op1:oper4) {
            if(s.equals(op1)) return true;
        }
        return false;
    }
    
    //判断是否是数字
    public boolean isfra(char c) {
        if(c>='0'&&c<='9') 
            {return true;}
        return false;
    }
    public boolean isfraop(char c) {
        if(c=='\''||c=='/') {
            return true;
        }
        return false;
    }
    
    //将String类型表达式转换成List<String>类型
    public List<String> Stringtolist(String str){
        List<String> infix = new ArrayList<String>();
        str=str.replace(" ", "");
        char op;
        String temp="";
        for(int i=0;i<str.length();i++) {
            op=str.charAt(i);
        if(isfra(op)||isfraop(op)) {
            temp+=op;
        } else if(isoper(op)) {
            if(!temp.isEmpty()) {
                infix.add(temp);
                temp="";
            }
            infix.add(op+"");
        }       
        }
        if(!temp.isEmpty()) {
            infix.add(temp);
            temp="";
        }
        return infix;
    }
    
    //将中缀表达式转换为后缀表达式
     public List<String> infixtopostfix(List<String> infix){
         List<String> postfix=new ArrayList<String>();
         Stack<String> s1=new Stack<String>();
         for (String str : infix) {
             if(str.equals("(")) {
                 s1.push(str);
             } 
             else if(str.equals(")")) {
                 while(!s1.peek().equals("(")) {
                     postfix.add(s1.pop());
                 }
                 s1.pop();
             } 
             else if(str.equals("+")||str.equals("-")||str.equals("×")||str.equals("÷")) {
                 while (s1.size() != 0 && getValue(s1.peek()) >= getValue(str)) {
                        postfix.add(s1.pop());
                    }
                    s1.push(str);
             } else {
                 postfix.add(str);
             }   
         }
         while (s1.size() != 0) {
                postfix.add(s1.pop());
            }
        return postfix;
     }
    
     //对后缀表达式进行计算
     public Fraction calculate(String str) {
         List<String> linfix=Stringtolist(str);
         List<String> lpostfix=infixtopostfix(linfix); 
         Stack<Fraction> s2=new Stack<Fraction>();
         Fraction f1;
         Fraction f2;
         Fraction answer;
         for(String cal:lpostfix) {
            if(!isoper(cal)) {
                Fraction f=Fraction.tofraction(cal);
                s2.push(f);
            } else {
                switch (cal) {
                case "+":
                    f1=s2.pop();
                    f2=s2.pop();
                    answer=f2.add(f1);
                    s2.push(answer);
                    break;
                case "-":
                    f1=s2.pop();
                    f2=s2.pop();
                    answer=f2.sub(f1);
                    s2.push(answer);
                    break;
                case "×":
                    f1=s2.pop();
                    f2=s2.pop();
                    answer=f2.mult(f1);
                    s2.push(answer);
                    break;
                case "÷":
                    f1=s2.pop();
                    f2=s2.pop();
                    answer=f2.div(f1);
                    s2.push(answer);
                    break;
                }               
            }
         }
         return s2.pop();   
     }
    
     //查重表达式的生成
     public List<String> getcnki(String str){
         List<String> linfix=Stringtolist(str);
         List<String> lpostfix=infixtopostfix(linfix);
         List<String> cnkiexp=new ArrayList<String>();
         Stack<String> st=new Stack<String>();
         String top1=null;
         String top2=null;
         for(String cal:lpostfix) {
                if(!isoper(cal)) {
                    st.push(cal);
                } else if(cal.equals("+")||cal.equals("-")||cal.equals("×")) {
                    cnkiexp.add(cal);
                    top1=st.pop();
                    top2=st.pop();
                    if(top2!="@") {
                        cnkiexp.add(top2);
                    }
                    if(top1!="@") {
                        cnkiexp.add(top1);
                    }
                    st.push("@");
                }
                else if(cal.equals("÷")) {
                    cnkiexp.add(cal);
                    top1=st.pop();
                    top2=st.pop();
                    cnkiexp.add(top2);
                    cnkiexp.add(top1);
                    st.push("@");
                }
             }
             return cnkiexp;    
         }
     
     //将List<String>类型表达式转换成String类型
     public String list2String(List<String> list) {
         String str1="";
         for(String s:list) {
             str1=str1+s+" ";
         }
         return str1;
     }
     
        }

Create类:题目和答案文档的生成
package myapp;

import java.io.*;
import java.util.HashMap;
import java.util.List;


public class Create {
    Expression expression=new Expression();
    Calc cal=new Calc();
    HashMap<String,String> map = new HashMap<String,String>();
    //在当前目录下生成练习题和答案
    public void cr(int n,int r) throws IOException {
        BufferedWriter btex=new BufferedWriter(new FileWriter(".\\Exercises.txt"));
        BufferedWriter btan=new BufferedWriter(new FileWriter(".\\Answers.txt"));
        for(int i=1;i<n+1;i++){
            String exps=expression.getexp(r);

            List<String> cnkiexp1=cal.getcnki(exps);
            String cnki1=cal.list2String(cnkiexp1); 
            boolean contains2 =false;
            if(cnkiexp1.get(0).equals("+")||cnkiexp1.get(0).equals("×")) {
                List<String> cnkiexp2=cnkiexp1;
                String t1=cnkiexp2.get(1);
                String t2=cnkiexp2.get(2);
                cnkiexp2.set(1, t2);
                cnkiexp2.set(2, t1);
                String cnki2=cal.list2String(cnkiexp2); 
                contains2 = map.containsKey(cnki2);
            }
            if(i==1) {map.put(cnki1,"");}
            boolean contains = map.containsKey(cnki1);
            if(contains==true||contains2==true) {
                exps=expression.getexp(r);
                cnkiexp1=cal.getcnki(exps);
                cnki1=cal.list2String(cnkiexp1);
                contains2 =false;
                if(cnkiexp1.get(0).equals("+")||cnkiexp1.get(0).equals("×")) {
                    List<String> cnkiexp2=cnkiexp1;
                    String t1=cnkiexp2.get(1);
                    String t2=cnkiexp2.get(2);
                    cnkiexp2.set(1, t2);
                    cnkiexp2.set(2, t1);
                    String cnki2=cal.list2String(cnkiexp2); 
                    contains2 = map.containsKey(cnki2);
                }
            }
            map.put(cnki1,"");
            
            Fraction answer=cal.calculate(exps);
            String answers=answer.toString();
            btex.write(i+". "+exps+"\r\n");
            btan.write(i+". "+answers+"\r\n");
        }
        btex.flush();
        btan.flush();
        btex.close();
        btan.close();
    }
    
}
Checkanswer:批改答卷
package myapp;

import java.io.BufferedReader;
import java.io.BufferedWriter;
import java.io.FileReader;
import java.io.FileWriter;
import java.io.IOException;
import java.util.ArrayList;
import java.util.List;

public class Checkanswer {
    
    public void check(String expath,String anpath) throws IOException{
        BufferedReader brex=new BufferedReader(new FileReader(expath));
        BufferedReader bran=new BufferedReader(new FileReader(anpath));
        BufferedWriter bwgrade=new BufferedWriter(new FileWriter(".\\Grade.txt"));
        List<String> Correct=new ArrayList<String>();
        List<String> Wrong=new ArrayList<String>();
        String an=null;
        String ex=null;
        while((an=bran.readLine())!=null) {
            ex=brex.readLine();
            int point=an.indexOf(".");
            String stran=an.substring(point+1);
            stran=stran.trim();
            String strex=ex.substring(point+1);
            strex=strex.trim();
            if(stran.equals(strex)) {           
                String cno=an.substring(0, point);
                Correct.add(cno);
            }else {
                String wno=an.substring(0, point);
                Wrong.add(wno);
            }
        }
        String corr=String.join(",",Correct); 
        String wr=String.join(",",Wrong); 
        bwgrade.write("Correct: "+Correct.size()+" ("+corr+")"+"\r\n");
        bwgrade.write("Wrong: "+Wrong.size()+" ("+wr+")");
        bwgrade.flush();
        bwgrade.close();    
    }
}
Run:主函数类,对输入命令进行处理,调用相应的方法
package myapp;

import java.io.FileNotFoundException;
import java.io.IOException;
import java.util.Scanner;
import java.util.regex.Matcher;
import java.util.regex.Pattern;

public class Run {

    public static void main(String[] args) throws IOException  {
        Scanner scan=new Scanner(System.in);
        String command=null;
        Create create=new Create();
        Checkanswer checkanswer=new Checkanswer();
        String nr="^\\-n\\s+\\d+\\s+\\-r\\s+\\d+$||^\\-r\\s+\\d+\\s+\\-n\\s+\\d+$";
        String ea="^\\-e\\s+\\S+\\s+\\-a\\s+\\S+$";
        int n = 0;
        int r = 0;
        String exercisesfile=null;
        String answersfile=null;
        System.out.println("小学四则运算题目生成程序");
        System.out.println("-r 题目中数值(该参数可以设置为1或其他自然数)");
        System.out.println("-n 题目个值(该参数可以设置为1或其他自然数)");
        System.out.println("-e 需要批改的答案的文件路径");
        System.out.println("-a 正确答案的文件路径"); 
        System.out.println("请按照下面的格式输入命令");
        System.out.println("例:-n 10 -r 10 或 -r 10 -n 10 (-r和-n命令需要一起使用)"); 
        System.out.println("例:-e D:\\\\myanswer.txt -a D:\\\\Answers.txt (-e和-a命令需要一起使用)");
        while(scan.hasNextLine()) {
            if (scan.hasNextLine()) {
                command = scan.nextLine();}            
        
        //检查命令是否正确
        Pattern pa = Pattern.compile(nr);
        Matcher ma = pa.matcher(command);
        Pattern p = Pattern.compile(ea);
        Matcher m = p.matcher(command);
        if(!(ma.matches()||m.matches())) {
            System.out.println("命令格式错误,请重新输入");
            continue;
        }
        //对命令进行分割
        String[] c=command.split("\\s+");
        if(c[0].equals("-n")&&c[2].equals("-r")) {
            n=Integer.parseInt(c[1]);
            r=Integer.parseInt(c[3]);
            create.cr(n,r);
            System.out.println("练习题目Exercises.txt和答案文件Answers.txt已生成,放置在本程序的当前目录下");
        }
        else if(c[0].equals("-r")&&c[2].equals("-n")){
            r=Integer.parseInt(c[1]);
            n=Integer.parseInt(c[3]);
            create.cr(n,r);
            System.out.println("练习题目Exercises.txt和答案文件Answers.txt已生成,放置在本程序的当前目录下");
        }
        if(c[0].equals("-e")&&c[2].equals("-a")) {
            exercisesfile=c[1];
            answersfile=c[3];
            try {
            checkanswer.check(exercisesfile,answersfile);}
            catch(FileNotFoundException e) {
                System.out.println("找不到指定文件,请重新输入正确的文件路径");
                continue;
            }
            System.out.println("批改文件Grade.txt已生成,放置在本程序的当前目录下");
        }
        System.out.println("请及时保存文件,再次使用程序时上一次生成的文件会被覆盖");
        //归零
        n=0;
        r=0;
        }   
        
    }
}

测试运行

生成10道题目:

1483675-20180930151313175-1430962339.png

1483675-20180930151337603-349131500.png

统计答案中对错的的数目:

1483675-20180930151745222-496478209.png

1483675-20180930151754547-668313608.png

生成10000题目:

1483675-20180930152029154-980920236.png

题目地址
答案地址

项目小结

此次项目,由我和夏浚杰同学一起结对编程,我们各负责一部分代码的编写。我们在设计功能时会提出各自的想法,经过讨论选择更合适的方法。在结对编程之后,我感受到了结对编程的优点在于,在我编写代码的过程中,夏浚杰同学会在旁边找出我的错误,让我能及时修改代码,这样提高了编程效率,节约时间。在结对编程中,夏浚杰同学提出了不同的想法,让我有所收获。

转载于:https://www.cnblogs.com/shawaux/p/9729226.html

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值