Uva10162
Give you a integer number N (1<=n<=2*10100). Please compute
S=11+22+33+…+NN
Give the last digit of S to me
Input
Input file consists of several N’s, each N a line. It is ended with N = 0.
Output
For each N give a line containing only one digit, which is the last digit of S
Sample Input
1
2
3
0
Sample Output
1
5
2
题意:求s的最后一位数
思路:一看范围在2*10^100内,很惆怅
经过打表发现,有循环节,100一圈
#include<iostream>
#include<stdio.h>
#include<string.h>
#include<algorithm>
#include<string>
using namespace std;
#define ll long long
#define mod 10
int map[101]={
0,
1,5,2,8,3,9,2,8,7,7,
8,4,7,3,8,4,1,5,4,4,
5,9,6,2,7,3,6,2,1,1,
2,8,1,7,2,8,5,9,8,8,
9,3,0,6,1,7,0,6,5,5,
6,2,5,1,6,2,9,3,2,2,
3,7,4,0,5,1,4,0,9,9,
0,6,9,5,0,6,3,7,6,6,
7,1,8,4,9,5,8,4,3,3,
4,0,3,9,4,0,7,1,0,0
};
ll pow(ll a,ll b)
{
ll ans=1;
ll base=a;
while(b!=0)
{
if(b&1!=0)
ans*=base%mod;
base*=base%mod;
b>>=1;
}
return ans%mod;
}
//ll map[10001];
int main()
{
ll n;
string s;
while(cin>>s)
{
//cout<<pow(n,n)<<endl;
/*ll ans=0;
for(int j=1;j<=200;j++)
{
ans=0;
for(int i=1;i<=j;i++)
ans+=pow(i,i);
cout<<ans%mod<<", ";
if(j%10==0)
cout<<endl;
}*/
if(s[0]=='0')
break;
int gg=0;
if(s.size()>2)
{
gg=s[s.size()-1]-48+(s[s.size()-2]-48)*10;
cout<<map[gg]<<endl;
}
else if(s.size()==1)
cout<<map[s[0]-48]<<endl;
else if(s.size()==2)
{
gg=(s[0]-48)*10+s[1]-48;
cout<<map[gg]<<endl;
}
//cout<<gg<<endl;
}
return 0;
}
Uva10539
Almost prime numbers are the non-prime numbers which are divisible by only a single prime number.In this problem your job is to write a program which finds out the number of almost prime numberswithin a certain range.
Input
First line of the input file contains an integer N (N ≤ 600) which indicates how many sets of inputsare there. Each of the next N lines make a single set of input. Each set contains two integer numberslow and high (0 < low ≤ high < 1012).
Output
For each line of input except the first line you should produce one line of output. This line containsa single integer, which indicates how many almost prime numbers are within the range (inclusive)low . . . high.
Sample Input
3
1 10
1 20
1 5
Sample Output
3
4
1
题意:给你一个区间[l,r],问你在这个区间内满足自身不是素数,而且只有一个素数因子的数有几个
思路:根据唯一分解定理(每个数都能分解成若干个素数的乘积),而此题要求只有一个素数因子的且自身不是素数,所以所求的数必定是一个prime^k,(k1,2,3,4,5,6,……N),以这条线为主线,写了个暴力,
先把素数筛出来,然后一个一个去检验,只要该素数的k次方在[l,r]之间,则该数必定符合条件,找到超出r的素数跳入下一个素数,直至素数本身比r大,这个一直超时,到网上观望了一下,发现新新大陆
用万能的log,对于任意一个素数prime, prime^k<n 两边去对数,解得k=log(n+0.1)/log(prime[i])
求得的是<n的所有的满足要求的,对于素数本身,要减去1,因为题目要求自身不是素数,具体见代码中体现
区间内则是f(r)-f(l-1)
#include<cstdio>
#include<cstring>
#include<cmath>
#define N 1000010
#define LL long long
int prime[N],num;
int vis[N];
void Oula(int n)
{
for (int i=2;i<=1000000;i++)
{
if (!vis[i]) prime[++num]=i;
for (int j=1;j<=num&&i*prime[j]<=1000000;j++)
{
vis[i*prime[j]]=1;
if (i%prime[j]==0) break;
}
}
}
LL qry(LL n)
{
LL ans=0;
for (int i=1;i<=num&&(LL)prime[i]*prime[i]<=n;i++)
ans+=log(n+0.1)/log(prime[i])-1;
return ans;
}
int main()
{
LL l,r;
Oula(N);
int T;
scanf("%d",&T);
while (T--)
{
scanf("%lld%lld",&l,&r);
printf("%lld\n",qry(r)-qry(l-1));
}
}