小学期作业

7 寻找区间和

#include <stdio.h>
#include <iostream>
int main()
{
	using namespace std;
	int len, SUM;
	int i = 0, j = 0;
	int sum = 0;
	int a[2010] = {0};
	cin >> len >> SUM;
	for (i = 0; i < len; i++)
		cin >> a[i];
	i = 0;
	sum = a[i];
	while (i <= j && j < len)
	{
		if (sum < SUM)
		{
			j++;
			sum += a[j];
		}
		else
		{
			if (sum == SUM)
				printf("%d %d\n", i, j);
			sum -= a[i];
			i++;
		}
	}
	return 0;
}

08A:滑动窗口求最值(单调队列)
1.暴力遍历

#include <stdio.h>
#include <iostream>
int FindMin(int i, int k);
int a[2010];
int main()
{
	using namespace std;
	int len, k;
	int sum = 0;
	cin >> len >> k;
	for (int i = 0; i < len; i++)
		cin >> a[i];
	for (int i = 0; i < len - k + 1; i++)
	{
		sum += FindMin(i,k);
	}
	cout << sum;
	return 0;
}
int FindMin(int i, int k)
{
	int min = i;
	for (int j = i; j < i + k; j++)
	{
		if (a[j] <= a[min])
			min = j;
	}
	return a[min] * a[min];
}

2.单调队列求滑动窗口最值: 虽然滑动窗口中不断有新元素加入和旧元素弹出,但是始终都有一个特点就是新元素都是从右指针r处加入的,旧元素都是从左指针l处弹出的。当一个元素如果是当前窗口的最大值,则它前面的值就不需要保存,因为只要它在窗口中,最值就不会变成其他的值,而对于它后面的比它小的元素则要保存,因为它一点弹出,最大值就要发生变化,需要保存后面的比它小的值。类似可推最小值。
————————————————
转载 --https://blog.csdn.net/weixin_41514525/article/details/113916744

#include <stdio.h>
#include <iostream>
using namespace std;
const int N = 100010;
int a[N]; int q[N];
int n, k;
void solve()
{
	int hh = 0, tt = -1, sum = 0;
	for (int i = 0; i < n; i++)
	{
		if (hh <= tt && q[hh] < i - k + 1)
			hh++;
		while (hh <= tt && a[q[tt]] >= a[i])
			tt--;
		q[++tt] = i;
		if (i >= k - 1)
			sum += a[q[hh]] * a[q[hh]];
	}
	cout << sum;
}
int main()
{
	cin >> n >> k; // 为n,k赋值
	for (int i = 0; i < n; i++)
		cin >> a[i];  //为数组赋值
	solve();
}

3.优先队列
9 区间任意最值(线段树)
遍历

#include <stdio.h>
#include <iostream>
int FindMax(int a, int b);
int a[2010];
int main()
{
	using namespace std;
	int len, n;
	int max, min; 
	int sum = 0;
	cin >> len >> n;
	for (int i = 0; i < len; i++)
		cin >> a[i];
	for (int i = 0; i < n; i++)
	{
		int b;
		cin >> min >> max;
		b = FindMax(min,max);
		cout << a[b] << endl;
	}
	return 0;
}
int FindMax(int x, int y)
{
	int j;
	int max = x - 1;
	for ( j = x-1; j < y; j++)
	{
		if (a[j] > a[max])
			max = j;
	}
	return max;
}

10. 连续区间的最大平均值

#include <iostream>
#include <stdio.h>
int a[100001] = { 0 }, sum[10001] = { 0 }, b[10001] = { 0 };
int FindSum(int i, int f)
{
	return (sum[i + f ] - sum[i])/f;
}
int main()
{
	using namespace std;
	int N, F, i, j = 0;
	int cnt = 0;
	int flag = 0;
	int sum1 = 0;
	sum[0] = 0;
	cin >> N>>F ;
	while (1)
	{
		int a1, s, m;
		int cnt1 = 0;
		cin >> a1 >> s >> m;
		for (i = 0 + j; i < m + j; i++)
		{
			a[i] = a1 + cnt1 * s;
			sum1 += a[i];
			sum[i+1] = sum1;
			cnt1++; // 计算s叠加次数
			cnt++;
			if (cnt > N)
			{
				flag = 1;
				break;
			}

		}
		if (flag)
			break;
		j = i;
	}
	int max = 0;
	for (i = 0; i < N - F + 1; i++)
	{
		int t = FindSum(i, F);
		if (t > max)
			max = t;
	}
	cout << max * 1000;
	return 0;
}

考试

1.给定多行,一行一个整数i,输出第i个素数(素数2是第1个素数),每个结果一行,最后一行有回车;直至输入结束

i<100010

例子

输入

1

2

5

3

输出

2

3

11

5
1.直接遍历构建素数表 (学习通运行不通过)

#include <iostream>
#define  N 100100
int isprime[N];
int main()
{
	using namespace std;
	int cnt = 0; // 记录素数的个数
	int prime = 1;
	isprime[cnt++] = 2;
	for (int i = 3; cnt < N; i++)
	{
		for (int j = 0; j < cnt; j++)
		{
			if (i % isprime[j] == 0)
			{
				prime = 0;
				break;
			}
			prime = 1;
		}
		if (prime)
		{
			isprime[cnt++] = i;
		}
	}
	int i;
	while (cin >> i)
	{
		cout << isprime[i -1] << endl;
	}
	return 0;
}

2.埃氏筛

//	1. 创建 大小为 N 的 bool 类型数组
//2. 将 bool 数组 的值全赋值为true
//3.筛掉所有素数的倍数,剩下的就是素数;
#include <stdio.h>
#include <iostream>
#define N 1300000
#define N1 100100
bool isPrim[N];
int count1[N1];

void  countPrimes() {

    for (int i = 0; i < N; i++)
        isPrim[i] = true;

    for (int i = 2; i * i < N; i++)
        if (isPrim[i])
            for (int j = i * i; j < N; j += i)
                isPrim[j] = false;

    int cnt = 1;
    for (int i = 2; i < N; i++)
        if (isPrim[i]) count1[cnt++] = i;
}
int main()
{
    using namespace std;
    int n;
    countPrimes();
    while (cin >> n)
    {
        cout << count1[n] << endl;
    }
    return 0;
}

创建n阶螺旋矩阵并输出。

#include<iostream>
using namespace std;
int a[100][100];
int split(int n)
{
	int cnt = 0;
	do {
		n /= 10;
		cnt++;
	} while (n);
	return cnt;
}
void func(int n)
{
	int i, j;
	int x = 0, y = -1;              //x,y表示当前数组要赋值的位置 
	int x_add = 0, y_add = 1;      //每次赋值时,数组下标x和y的增量 
	int num = n, num_add_1 = n, num_add_2 = n;      //num:移动方向发生变化的转变点,num_add:每次转变时num的增量 

	for (i = 1; i <= n * n; i++)
	{
		x += x_add;
		y += y_add;
		a[x][y] = i;
		if (i == num)
		{
			if (y_add == 1 || y_add == -1)    // row - column 横向变纵向
			{
				x_add = y_add - x_add;
				y_add = 0;
				num_add_2--;
				num += num_add_2;
			}
			else                               //colunm - row 纵向变横向
			{
				y_add = y_add - x_add;
				x_add = 0;
				num_add_1--;
				num += num_add_1;
			}
		}
	}
	int cnt = split(n * n);
	for (i = 0; i < n; i++)
	{
		j = 0;
		if (n <= 3) 
			printf("%d ", a[i][j]);
		else if(n > 3 && n <=25)
			printf("%2d ", a[i][j]);
		else if (n > 25)
			printf("%3d ", a[i][j]);   // 保证第一列的最大位数与第一列的最大数相同 不产生多余空格
		for (j = 1; j < n; j++)
		{
			switch (cnt)
			{
			case 1:
				if (j == n - 1)        // 判断是否是最后一行,如果是,不打印空格
					printf("%d", a[i][j]); 
				else
					printf("%d ", a[i][j]); 
				break;
			case 2:
				if (j == n - 1)
					printf("%2d", a[i][j]);
				else
					printf("%2d ", a[i][j]);
				break;
			case 3:
				if (j == n - 1)
					printf("%3d", a[i][j]);
				else
					printf("%3d ", a[i][j]);
				break;
			case 4:
				if (j == n - 1)
					printf("%4d", a[i][j]);
				else
					printf("%4d ", a[i][j]);
				break;
			default:break;
			}
		}
		printf("\n");
	}
}
int main()
{
	int n;//方阵阶数 
	int i; //循环变量 
	int b[25];
	int cn = 0;
	while (cin >> n)
	{
		func(n);
	}
}

创建nm阶螺旋矩阵并输出。*

#include<iostream>
using namespace std;
int a[100][100];
void func(int n, int m)
{
	int i, j;
	int x = 0, y = -1;              //x,y表示当前数组要赋值的位置 
	int x_add = 0, y_add = 1;      //每次赋值时,数组下标x和y的增量 
	int num = m, num_add_1 = m, num_add_2 = n;       //num:移动方向发生变化的转变点,num_add:每次转变时num的增量 

	for (i = 1; i <= n * m; i++)
	{
		x += x_add;
		y += y_add;
		a[x][y] = i;
		if (i == num)
		{
			if (y_add == 1 || y_add == -1)
			{
				x_add = y_add - x_add;
				y_add = 0;
				num_add_2--;
				num += num_add_2;
			}
			else
			{
				y_add = y_add - x_add;
				x_add = 0;
				num_add_1--;
				num += num_add_1;
			}
		}
	}
	for (i = 0; i < n; i++)
	{
		for (j = 0; j < m; j++)
		{
			printf("%4d", a[i][j]);
		}
		cout << endl;
	}
}
int main()
{
	int n, m; //方阵阶数 
	int i; //循环变量 
	int c[25], b[25];
	int cnt = 0;
	while(cin >> n >>m)
	{
		if (n == 0 && m == 0)
			break;
		c[cnt] = n; b[cnt] = m;
		cnt++;
	}
	for (i = 0; i < cnt; i++)
	{
		func(c[i], b[i]);
	}
}

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值