算法学习--Day6

Posted pinging

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了算法学习--Day6相关的知识,希望对你有一定的参考价值。

题目描述

实现一个加法器,使其能够输出a+b的值。

输入描述:

输入包括两个数a和b,其中a和b的位数不超过1000位。

输出描述:

可能有多组测试数据,对于每组数据,
输出a+b的值。
示例1

输入

2 6
10000000000000000000 10000000000000000000000000000000

输出

8
10000000000010000000000000000000


#include "stdio.h"
#include "iostream"
#include "string.h"
using namespace std;


struct bigInteger{
    int digit[1000];
//to save the numbers
    int size;
    //to save the array‘s size
    void init(){
        for (int i = 0; i <1000 ; ++i) {
            digit[i] = 0;
        }
        size = 0;
    }
    //this is an init function.

    void set(char str[]){  //to put a string into our array.
        init();
        int L = strlen(str);
        int ans=0;
        int times=0;
        int c=1;
        //we use the c to multiple 1、10、.....100000....
        for (int i = L -1; i >=0 ; i--) {
            ans+=(str[i]-0)*c;
            times++;
            c*=10;
            if(times==4 || i==0){
                //i=0 to avoid the final array not being saved.
                digit[size++] = ans;
                times = 0;
                c = 1;
                ans = 0;
            }
        }
    }

    bigInteger operator + (const bigInteger &A) const {
        bigInteger ret;
        ret.init();
        int nextMove = 0;

        for (int i = 0; i <size|| i<A.size ; ++i) {
            int tmp = digit[i]+ A.digit[i] +nextMove;
            nextMove = tmp /10000;
            ret.digit[ret.size++] = tmp%10000;
        }
        if(nextMove!=0){
            ret.digit[ret.size++] = nextMove;
        }
        return ret;
    };

    void output(){
        for (int i = size-1; i >=0 ; i--) {
            if(i!=size-1) printf("%04d",digit[i]);
            else{
                printf("%d",digit[i]);
            }

        }
        cout<<endl;
    }
}a,b,c;

int main(){
    char str1[1001],str2[1001];
    while (scanf("%s%s",str1,str2)!=EOF){
        a.set(str1);
        b.set(str2);
        c = a+b;
        c.output();


    }

    return 0;
}

 

以前写密码学设计的时候就一直听说有高精度的设计,今天终于也实现了一把高精度的加法。因为从前没有接触过,所以也把思想放这里,方便以后查阅。

 

高精度的算法实现的思想大致为:

①创建一个结构体,在结构体中定义数组,将很大的数分成几个部分装到这个数组中。

②之后重构运算符,将两个数字一一对应的部分相加,并考虑进位的情况。

③定义输入、输出函数,将字符串数组输入并处理到结构体的数组中。

不过结构体中的细节要考虑一些,毕竟算法比较严谨。

 

 

之后我将近期写的部分代码放上来。

 

题目描述

求正整数N(N>1)的质因数的个数。 相同的质因数需要重复计算。如120=2*2*2*3*5,共有5个质因数。

输入描述:

可能有多组测试数据,每组测试数据的输入是一个正整数N,(1<N<10^9)。

输出描述:

对于每组数据,输出N的质因数的个数。
示例1

输入

120

输出

5


#include "stdio.h"
#include "iostream"
using namespace std;
int prime[100000];
int flag[100000];
int f=0;
int init(){
    for (int i = 0; i < 100000; ++i) {
        flag[i] = 1;
    }
    for (int j = 2; j < 10000; ++j) {
        if(flag[j]==0) continue;
        prime[f++] = j;
        for (int i = j*j; i < 10000; i+=j) {
            flag[i] = 0;
        }
    }
    return 0;
}

int main(){
    init();
    int n;
    while (scanf("%d",&n)!=EOF){
        int primeCup[100];
        int perCount[100];
        int count=0;
        for (int i = 0; i < f; ++i) {
            if(n%prime[i] == 0){
                primeCup[count] = prime[i];
                perCount[count] = 0;
                while (n % prime[i] == 0){
                    perCount[count]++;
                    n/=prime[i];
                }
                count++;
                if(n==1) break;
            }

        }
        if(n!=1){
            primeCup[count] = n;
            perCount[count++] = 1;
        }
int ans=0;
        for (int j = 0; j < count; ++j) {
            ans+=perCount[j];
        }
        cout<<ans<<endl;
    }


    return 0;
}

 

 

题目描述

Output the k-th prime number.

输入描述:

k≤10000

输出描述:

The k-th prime number.
示例1

输入

3
7

输出

5
17

//Prime Number

#include "stdio.h"
#include "iostream"
#include "math.h"
using namespace std;
int prime[100000];
int f=0;
int init(){
    int flag[100000];
    for (int i = 0; i <100000 ; ++i) {
        flag[i]=1;
    }
    for (int j = 2; j <=100000 ; ++j) {
        if(flag[j]==0) continue;
        else{
            prime[f++] = j;
            for (int i = j*j; i <= 100000; i+=j) {
                flag[i] = 0;
            }
        }
    }
    return 0;
}
int main(){
    init();
    int n ;
    while (scanf("%d",&n)!=EOF){
        cout<<prime[n-1]<<endl;
    }
    return 0;
}

这是素数的处理方法,使用预处理先行处理之后就很方便得到了。

 

题目描述

输入两个正整数,求其最大公约数。

输入描述:

测试数据有多组,每组输入两个正整数。

输出描述:

对于每组输入,请输出其最大公约数。
示例1

输入

49 14

输出

7
//最大公约数
#include "stdio.h"
#include "iostream"
using namespace std;
int init(int a, int b){
    if(b==0){ return a;}
    else{
        return init(b,a%b);
    }
}

int main(){
    int a,b;
    while (scanf("%d%d",&a,&b)!=EOF){
        a>=b?cout<<init(a,b)<<endl:cout<<init(b,a)<<endl;
    }
}

 

 

题目描述

输入一个整数,将其转换成八进制数输出。

输入描述:

输入包括一个整数N(0<=N<=100000)。

输出描述:

可能有多组测试数据,对于每组数据,
输出N的八进制表示数。
示例1

输入

7
8
9

输出

7
10
11

//八进制

#include "stdio.h"
#include "iostream"
using namespace std;

int main(){
    int n;
    while (scanf("%d",&n)!=EOF){
        int ans=0,flag=0;
        int fin[100];

        while (n!=0){
            ans=n%8;
            n/=8;
            fin[flag++]=ans;
        }
        for (int i = flag-1; i >=0 ; i--) {
            cout<<fin[i];
        }
        cout<<endl;
    }
}

这是进制转换类型的题目,这种题目比较基础,但是考的也挺多。

 

 

所以下面我放上去通用的题目,输入任意进制 转化为任意进制。

例如:15 Aab3 7

将15进制转换为7进制并输出。

//数值转换

#include "iostream"
#include "string.h"
#include "stdio.h"
using namespace std;

int main(){
    int n,m;
    char input[100];
    while (scanf("%d%s%d",&n,input,&m)!=EOF){
        int length = strlen(input);
        int first=1;
        int ans = 0;
        for (int i = length-1; i >=0; i--) {
            int x;
            if(input[i]>=0&&input[i]<=9) {
                x = input[i] - 0;
            }
            if(input[i]>=a&&input[i]<=z){
                x = input[i] - a +10;
            }
            if(input[i]>=A&&input[i]<=Z){
                x = input[i] - A+10;
            }
            ans+=x*first;
            first=first*n;

        }
        char output[100];
        int flag=0;
        do{
            int y =ans % m;
            if (y>=10) {output[flag] = (y-10)+A;}

            else {output[flag] = y+0;}

            flag ++;
            ans/=m;
        }while (ans);
        for (int j = flag-1; j >=0 ; j--) {
            cout<<output[j];
        }
        cout<<endl;
    }
}

 

 

题目描述

输入两个不超过整型定义的非负10进制整数A和B(<=231-1),输出A+B的m (1 < m <10)进制数。

输入描述:

输入格式:测试输入包含若干测试用例。每个测试用例占一行,给出m和A,B的值。
当m为0时输入结束。

输出描述:

输出格式:每个测试用例的输出占一行,输出A+B的m进制数。
示例1

输入

8 1300 48
2 1 7
0

输出

2504
1000

//
// Created by 陈平 on 2018/4/22.
//又一板 A+B
#include "stdio.h"
#include "iostream"
#include "math.h"
using namespace std;
long long a,b;
int mFunction(int m, long long a){
    int con[100];
    int flag = 0;

    while (a!=0){
        con[flag] = a%m;
        a/=m;
        flag++;
    }
    for (int i = flag-1; i >=0 ; i--) {
        cout<<con[i];
    }
    cout<<endl;
    return 0;
}
int main(){
int m;
    while (scanf("%d",&m)!=EOF&&m!=0){
        scanf("%lld%lld",&a,&b);
        long long fin = a+b;
        if (a==0&b==0) cout<<0<<endl;
        else mFunction(m,fin);

    }
    return 0;
}

 

 

 

以上是关于算法学习--Day6的主要内容,如果未能解决你的问题,请参考以下文章

Python之路,Day6 - 面向对象学习

Python学习笔记day6

Python全栈开发,Day6 - 模块学习

iOS学习day6

python学习之路day6

2016-10-15坚持学习Day6组合模式