【蓝桥杯】历届试题 油漆面积

问题描述

资源限制
时间限制:2.0s 内存限制:256.0MB
问题描述  
X星球的一批考古机器人正在一片废墟上考古。该区域的地面坚硬如石、平整如镜。管理人员为方便,建立了标准的直角坐标系。每个机器人都各有特长、身怀绝技。它们感兴趣的内容也不相同。经过各种测量,每个机器人都会报告一个或多个矩形区域,作为优先考古的区域。矩形的表示格式为(x1,y1,x2,y2),代表矩形的两个对角点坐标。为了醒目,总部要求对所有机器人选中的矩形区域涂黄色油漆。
  小明并不需要当油漆工,只是他需要计算一下,一共要耗费多少油漆。
  其实这也不难,只要算出所有矩形覆盖的区域一共有多大面积就可以了。
  注意,各个矩形间可能重叠。
  本题的输入为若干矩形,要求输出其覆盖的总面积。
  
输入格式  
第一行,一个整数n,表示有多少个矩形(1<=n<10000)
  接下来的n行,每行有4个整数x1 y1 x2 y2,空格分开,表示矩形的两个对角顶点坐标。
  (0<= x1,y1,x2,y2 <=10000)
  
输出格式  
  一行一个整数,表示矩形覆盖的总面积面积。

样例输入1

3
1 5 10 10
3 1 20 20
2 7 15 17

样例输出1

340

样例输入2

3
5 2 10 6
2 7 12 10
8 1 15 15

样例输出2

128

解题思路

1、一开始看到题目,很自然想到根据四点计算面积,并依次加上未重合的面积,但是计算过于复杂。后来学习别人的思路,用数组直接将符合要求的点标记,最后计算总共被标记的面积即可,简单粗暴快捷。
2、用面积表示,相当于一个100平方厘米正方形,将其分为10X10的方格,每一方格代表面积即为1平方厘米。因此,被标记小方格个数即为被标记面积。
3、用整型数组内存会过大,所以选择bool数组。
4、另外,网上搜索很多答案后确定,第一个测试用例答案错误,故得分83分。

#include<iostream>
using namespace std;
bool res[10001][10001]={0};
int main()
{
       int n;
       cin>>n;
       int a,b,c,d;
       for(int i=0;i<n;i++)
       {
              cin>>a>>b>>c>>d;
              if(a>c)
              {
                     int tmp=a;
                     a=c;
                     c=tmp;
              }
              if(b>d)
              {
                     int tmp=b;
                     b=d;
                     d=tmp;
              }
              for(int p=a;p<c;p++)
              {
                     for(int q=b;q<d;q++)
                            res[p][q]=1;
              }      
       }
       int num=0;
       for(int i=0;i<10001;i++)
       {
              for(int j=0;j<10001;j++)
              {
                     if(res[i][j]==1)
                        num++;
              }
       }
       cout<<num;
       return 0;
 }
<think>好的,用户想了解蓝桥杯比赛中与油漆相关的题目及解题思路,还希望看到示例代码。首先,我需要回忆蓝桥杯历届真题中涉及的油漆问题。记得第八届蓝桥杯JavaA组省赛有一道关于计算油漆消耗量的题目,参考引用[1]提到的内容,可能需要计算多个矩形区域的面积。此外,可能还有其他类型的题目,比如动态规划中的涂色问题,如引用[2]提到的房屋涂色最小成本问题,或者引用[3]提到的座位选择问题,涉及组合数学。 用户的问题主要集中在解题思路示例代码上,因此我需要分类型整理常见的油漆问题类型。首先,面积计算类问题,可能涉及几何计算,比如多个矩形的并集面积,避免重复计算。其次,动态规划类问题,如相邻房屋不能同色,需要状态转移方程。还有可能是排列组合问题,例如选择特定数量的座位涂色后的可能性计算。 针对面积计算类,解题思路通常是利用扫描线算法或者离散化处理,但蓝桥杯可能更倾向于基础的遍历或差分数组方法,尤其是当坐标范围有限时。比如,引用[1]的问题,可能需要计算所有选中矩形区域的总面积,这时候可以使用二维差分数组来高效计算覆盖区域,最后累加所有被覆盖的位置数目即为油漆用量。 动态规划类问题,如引用[2],需要定义状态数组,比如每个位置涂不同颜色时的最小成本,并确保相邻颜色不同。状态转移方程是关键,每一步的选择依赖于前一步的不同颜色状态的最小值。 对于示例代码,面积问题可以用二维数组模拟覆盖区域,或者使用差分优化。动态规划问题则需要构建dp数组,并确实现状态转移。 需要确认用户具体指的是哪种类型的油漆问题。但根据提供的引用,可能第八届的题目更相关。所以,首先解释矩形面积问题,然后动态规划的问题,并分别给出思路代码示例。同时,需要确保代码语法确,符合用户要求的格式,比如Python代码块。 最后,生成相关问题,引导用户进一步思考,如优化方法、其他变种问题等。同时,注意引用标记的确添加,例如引用[1][2]分别在对应的解题思路后标注。</think>在蓝桥杯竞赛中,油漆相关题目常涉及动态规划、几何计算或组合数学。以下结合真题类型整理解题思路与代码示例: --- ### 一、矩形覆盖面积计算(引用[1]) **题目场景**:计算多个矩形区域的总油漆消耗量,每个矩形涂黄色油漆,要求避免重复计算重叠区域。 **解题思路**: 1. **差分数组法**:若坐标范围较小(如网格坐标系),使用二维差分数组记录覆盖次数,最后统计非零区域总面积 2. **离散化+扫描线**:若坐标范围较大,需离散化后按扫描线算法计算并集面积 **示例代码(差分数组法)**: ```python def calculate_paint_area(rectangles): max_size = 1000 # 假设坐标范围0-1000 diff = [[0]*(max_size+2) for _ in range(max_size+2)] for x1, y1, x2, y2 in rectangles: diff[x1][y1] += 1 diff[x1][y2+1] -= 1 diff[x2+1][y1] -= 1 diff[x2+1][y2+1] += 1 # 二维前缀还原覆盖次数 area = 0 for i in range(max_size+1): for j in range(max_size+1): if i > 0: diff[i][j] += diff[i-1][j] if j > 0: diff[i][j] += diff[i][j-1] if i>0 and j>0: diff[i][j] -= diff[i-1][j-1] if diff[i][j] > 0: # 被覆盖区域 area += 1 return area ``` --- ### 二、房屋涂色最小成本(引用[2]) **题目场景**:相邻房屋不能涂相同颜色,求涂色最小成本。 **动态规划解法**: 1. **状态定义**:$dp[i][c]$ 表示第$i$间房子涂颜色$c$时的前$i+1$间最小总成本 2. **状态转移**:当前颜色需与前一间不同,例如: $$ dp[i][red] = \min(dp[i-1][blue], dp[i-1][green]) + cost[i][red] $$ **示例代码**: ```python def min_cost(costs): n = len(costs) dp = [[0]*3 for _ in range(n)] dp[0] = costs[0] # 初始化第一间 for i in range(1, n): dp[i][0] = min(dp[i-1][1], dp[i-1][2]) + costs[i][0] dp[i][1] = min(dp[i-1][0], dp[i-1][2]) + costs[i][1] dp[i][2] = min(dp[i-1][0], dp[i-1][1]) + costs[i][2] return min(dp[-1]) # 测试输入:每行代表红/蓝/绿的成本 print(min_cost([[17,2,3],[16,5,1],[14,3,10]])) # 输出应为 2+1+3=6 ``` --- ### 三、座位选择问题(引用[3]) **题目场景**:蒂娜涂k个座位后,拉胡尔选择未涂色的座位,蒂娜再选任意非拉胡尔座位。 **组合数学思路**: 1. 总共有$n$个座位,蒂娜涂$k$个,剩余$n-k$个未涂 2. 拉胡尔选择$n-k$中的1个,蒂娜有$n-1$种选择 3. 总方案数:$C(n, k) \times (n-k) \times (n-1)$ ---
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值