PAT 乙级 1024 科学记数法

好久不更新博客了(虽然也没人看……水平有限),最近在刷PAT,这道题花了半个小时,觉得有必要写到博客里,先贴题。
这里写图片描述

题目要求是把科学记数法进行转换,输出非科学记数法的数字。
步骤如下:
1.分别录入“+-“号,数字部分和指数部分。
2.根据正负号首先决定是否在输出数字前输出负号“-”
3.判断小数点的移动方向,是左还是右。
4.如果小数点需要向右移动,则分三种情况(1)小数点移动过程中不需要补零【小数点后的数字位数小于E后面的指数】(2)小数点移动过程中正好不需要补零【小数点后的数字位数正好等于E后面的指数】(3)小数点移动过程中需要补零【小数点后的数字位数大于E后面的指数】。以上三种情况分别处理。
5.如果小数点向左移动,则首先输出“0.”,然后补零,然后输出后续数字

代码中有个个人认为有必要说一下的地方

scanf("%c%c.%[0-9]E%d", &head, &a[0], a + 1, & ex);

这个语句里的第一个“%c”把“+-”符号存到了字符变量head里面,第二个“%c”把第一个数字存储到了字符数组a[0]里面,后面的“.”跳过了小数点,紧接着的“%[0-9]E”这是正则表达式,作用是录入后面的所有数字,遇到非数字则结束,后面的“E”跳过了E的录入,最后的“%d”录入了E后面的指数部分。
也就是说这个语句执行完毕后,各变量的值应该是如下的情况
输入:+1.23400E-03
变量状态:
字符变量 head=‘+’;
字符数组 a=”123400“;
整数变量 ex=-3;

贴上代码(可直接提交到PAT):

#include <iostream>
#include <stdio.h>
#include <string.h》

using namespace std;

int main()
{
    char head, a[9999] = { 0 };
    int ex = 0, i = 0//如果用的是VS就把下面这行注释取消了,
    //scanf_s("%c%c.%[0-9]E%d", &head, sizeof(char), &a[0], sizeof(char), a + 1, sizeof(char) * 998 ,& ex);
    //如果用的是VS就注释下面这行
    scanf("%c%c.%[0-9]E%d", &head, &a[0], a + 1, & ex);
    if (head == '-')
        cout << "-";
    if (ex >= 0)
    {
        //如果小数点后的数字位数小于E后面的指数(需要补零)
        if (strlen(a) - 1 < ex)
        {
            for (i = 0; a[i] != '\0'; i++)
            {
                //避免出现输入 +0.1234E+E+5 后 输出 012340情况
                if (i == 0 && a[i] == '0')
                    continue;
                cout << a[i];
            }
            //计算需要补零的数量并输出指定位数的零
            for (int j = 0; j < ex - i + 1; j++)
                cout << 0;
        }
        //如果小数点后的数字位数大于E后面的指数(不需要补零)
        else if (strlen(a) - 1 > ex)
        {
            for (i = 0; a[i] != '\0'; i++)
            {
                //避免出现输入 +0.1234E+E+2 后 输出 012.34情况
                if (i == 0 && a[i] == '0')
                    continue;
                if (i == 1 + ex)
                {
                    //输出到小数点的位置时额外输出小数点
                    cout << "." << a[i];
                    continue;
                }
                cout << a[i];
            }
        }
        else
        {
            //如果小数点后的数字位数等于E后面的指数(不需要补零)
            for (i = 0; a[i] != '\0'; i++)
            {
                //避免出现输入 +0.1234E+E+4 后 输出 01234情况
                if (i == 0 && a[i] == '0')
                    continue;
                cout << a[i];
            }
        }
    }
    else
    {
        cout << "0.";
        for (int j = 0; j != ex + 1; j--)
            cout << "0";
        for (i = 0; a[i] != '\0'; i++)
        {
            cout << a[i];
        }
    }
    //如果用的是VS就取消注释下一行
    //system("pause");
}

猜你喜欢

转载自blog.csdn.net/kongming07/article/details/79944994