个人技术分享

一、big LITTLE

问题描述

为了应对灵活多变的市场需求,CPU厂家在规划产品时,往往预先设计一些核心模块和其他模块,根据市场需求把君干个模块组合起来作为一个型号生产和销售。Outel公司推出了第13代UncoreCPU。此系列CPU 有两类核心模块:一类是性能模块,每个模块目有1个性能核心,其线程数为2;另一类是能效模块,每个模块具有4个能效核心,每个能效核心的线程数为1(也就是说,单个能效模块的总线程数为 4)。输入一个 CPU 总核心模块数 M 和总线程数T,计算性能模块数 Mp 和能效模块数 ME。

输入格式

一行,两个整数 M和T,分别表示总核心模块和总线程数。(1<C<1000000000,2<T<2000000000,保证存在非负整数解)

输出格式

一行,两个整数 MP和 ME,分别表示性能模块数和能效模块数。

样例输入/输出

7 16
6 1

解释

6个性能模块,1个能效模块,总核心模块数为6+1=7,总线程数为6x2+1x4=16。

参考代码:
#include<iostream>
using namespace std;
int main()
{
	int m,t;
	cin>>m>>t;
	int x,y;
	y=(t-2*m)/2;
	x=m-y;
	cout<<x<<" "<<y;
	return 0;
}

二、猴子上楼梯

问题描述

顽皮的小猴子上楼梯,它可以一次走一级台阶,也可以一次走三级台阶,但绝不会一次走两级台阶。给定楼梯总台阶级数",求总共有多少种不同的上楼梯方案。

输入格式

一个正整数 n,表示楼梯的总台阶数。(n ≤ 50)

输出格式

一个正整数n,表示上楼梯方案数。

样例输入/输出
10
28

参考代码:
#include<iostream>
using namespace std;
long long f[55];
int main()
{
	f[0]=f[1]=f[2]=1;
	for(int i=3;i<=50;i++)
		f[i] = f[i-1]+f[i-3];
	int n;
	cin >> n;
	cout << f[n];
	return 0;
}

三、质数对

问题描述

给你一个长度为 n 的数组,请你计算有多少个下标对(i,j) 满足i<j 且 a[i]+ a[j]是质数。

输入格式

第一行一个数字n。(1≤n≤2000)
第二行n个数字。(任意一个数字ai 满足1≤ai≤ 100000)

输出格式

符合要求的质数对个数。

样例输入/输出

5

1 2 3 4 5

5
解释

符合条件的有(a[i],a[j])对有(1,2)、(1,4)、(2,3)、(2,5)、(3,4)。

参考代码:
#include<iostream>
using namespace std;
bool prime[200010];
int a[2005];
int main()
{
	for(int i=2;i<=200000;i++)	prime[i]=1;
	for(long long i=2;i<=200000;i++)
	{
		if(prime[i])
		{	for(long long j=i*i;j<=200000;j+=i)
				prime[j]=false;
		}
	}
	int n;
	cin >> n;
	for(int i=0;i<n; i++)
		cin >> a[i];
	int cnt=0;
	for(int i=0;i<n; i++)
	{
		for(int j=i+1; j<n; j++)
		{
			if(prime[a[i]+a[j]])
				cnt++;
		}
	}
	cout << cnt;
	return 0;
}

四、进制转换

问题描述

给定你两个数字x和y和一个字符串n,x代表字符串n的进制。
请输出n在y进制下的格式。

输入格式

第一行两个数字和一个字符申,分别代表x,y和n。(2≤x≤10,2≤y≤10,在x进制下n的数值满足0≤n≤(100 000)10)保证输入一定合法,且n不以0开头。

输出格式

一行一个数字,即y进制下的字符串 n。

样例输入/输出

4 5 12
11

解释

4进制下,字符串 12的真实值为6(6=1x4+2);在5进制下,6的字符串形式为11(6=1x5+1),对于n 建议用字符串输入。

参考代码:
#include<iostream>
#include <cstdio>
#include <cmath>
using namespace std;
int bit[100];
int main() 
{
	int x,y,n;
	cin>>x>>y>>n;
	int to_10=0;
	int p=0;
	int sum = 0;
	while(n)
	{
		sum += n%10*pow(x,p++)+0.1;
		n/=10;	
	}
	p=0;
	while(sum)
	{
		bit[p++]= sum%y;
		sum/=y;
	}
	for(int i=p-1;i>=0;i--)
		cout << bit[i];
	return 0;
}

五、不平衡数

问题描述

        平衡树也叫 AVL,在 AVL 树中任意节点的两颗子树的最大高度差都不超过1。现在,Bob 自己定义了一个概念,叫做“不平衡树”

  1.  一个树的和 S= R+ SL+ SR,其中 R 表示根节点的值,SL和 SR分别表示左右子树的和。空树的和 S= 0。
  2. 若树有两个子树,则它的不平衡度U =|SL- SR|,即“左子树和”与“右子树和”的差的绝对值(大减小)。若树仅有一个子树,则它的不平衡度U=UL,(仅左子树,不平衡度等于左子树的不平衡度)或U=UR(仅右子树,不平衡度等于右子树的不平衡度)。若树没有子树,则它的不平衡度 U= 0。

        现在,我们会根据前序遍历的顺序给出树上每个节点的值,0 代表空节点,你要输出这个树上所有节点的最大不平衡度。

输入格式

第一行一个数字n,代表节点个数。(1≤n≤100000)
第二行共 2n+1个整数,代表前序遍历节点的值。 (0 表示空节点,非空节点值x 的范围满足 -100000<=x<0 或 0< x=< 100000)

输出格式

输出该树上所有节点的最大的不平衡度,

样例输入/输出

3 209 1 0 0 0 100 10 0 0 200 0 0
190

解释

按照前序遍历顺序,各个节点的和S依次为:520,210,1,310,10,200

按照前序遍历顺序,各个节点不平衡度U依次为:100,0,0,190,0,0。

参考代码:
#include<iostream>
#include<cmath>
using namespace std;
typedef struct TreeNode 
{
	int data;	//节点值
	int av1;	//不平衡值
	int sum;	//子数和
	TreeNode* Lchild;	//左孩子
	TreeNode* Rchild;	//右孩子
}*Tree, TreeNode;
int ans=0;
//前序创建二叉树
void CreateTree(Tree& T)
{
	int x;
	cin >> x;
	if(x==0)
	{
		T = NULL;
		return;
	} 
	else 
	{
		T= new TreeNode;
		T->data = x;
		CreateTree(T->Lchild);
		CreateTree(T->Rchild);
	}
}
void dfs(Tree& T)
{
	if(T->Lchild==NULL && T->Rchild==NULL)
	{
		T->av1 =0;
		T->sum = T->data;
	}
	else if(T->Lchild==NULL)
	{
		dfs(T->Rchild);
		T->sum =T->Rchild->sum + T->data;
		T->av1 =T->Rchild->av1;
	}
	else if(T->Rchild==NULL)
	{
		dfs(T->Lchild);
		T->sum =T->Lchild->sum+T->data;
		T->av1 =T->Lchild->av1;
	}
	else
	{
		dfs(T->Lchild);
		dfs(T->Rchild);
		T->sum =T->Lchild->sum + T->Rchild->sum + T->data;
		T->av1 = abs(T->Lchild->sum - T->Rchild->sum);
	}
	ans = max(ans,T->av1);
}
int main()
{
	Tree T;
	CreateTree(T);
	dfs(T);
	cout << ans;
	return 0;
}
//3 209 1 0 0 0 100 10 0 0 200 0 0