Cake ZOJ - 3537(判断凸包模板+最优三角剖分+区间dp详解)

zoj3537(区间dp) 最有三角形划分,凸包不会也抄了别人的凸包代码一直wa不明觉厉,不过dp算是想对了; #include #include #include #include #include using namespace std; typedef long long lld; #define oo 0x3f3f3f3f #define mod 1000000007 #define maxn 300+5 int 阅读详情

Cake ZOJ - 3537

 You want to hold a party. Here's a polygon-shaped cake on the table. You'd like to cut the cake into several triangle-shaped parts for the invited comers. You have a knife to cut. The trace of each cut is a line segment, whose two endpoints are two vertices of the polygon. Within the polygon, any two cuts ought to be disjoint. Of course, the situation that only the endpoints of two segments intersect is allowed.

The cake's considered as a coordinate system. You have known the coordinates of vexteces. Each cut has a cost related to the coordinate of the vertex, whose formula is costi, j = |xi + xj| * |yi + yj| % p. You want to calculate the minimum cost.

NOTICE: input assures that NO three adjacent vertices on the polygon-shaped cake are in a line. And the cake is not always a convex.

Input

There're multiple cases. There's a blank line between two cases. The first line of each case contains two integers, N and p (3 ≤ N, p ≤ 300), indicating the number of vertices. Each line of the following N lines contains two integers, x and y (-10000 ≤ x, y ≤ 10000), indicating the coordinate of a vertex. You have known that no two vertices are in the same coordinate.

Output

If the cake is not convex polygon-shaped, output "I can't cut.". Otherwise, output the minimum cost.

Sample Input

3 3
0 0
1 1
0 2

Sample Output

0
题意:

给定n个点的坐标,先问这些点是否能组成一个凸包,如果是凸包,问用不相交的线来切这个凸包使得凸包只由三角形组成,根据 cost(i, j) = |xi + xj| * |yi + yj| % p 算切线的费用,问最少的切割费用。

分析:

首先当然是要先判断是否是凸包了

因为之前没有写过凸包的题目所以这里就写一下判断凸包的算法


Andrew算法:

首先把所有点按照x从小到大排序,(如果x相同,按照y从小到大排序),删除重复点后得到的序列
p1,p2,....p1,p2,.... 然后把p1,p2p1,p2放到凸包中,相当于入栈。从p3p3开始,当新点在凸包“前进方向的左侧时继续即新点在栈顶点的左侧时入栈,如果在右侧,就依次删除最近加入的点,即删除栈顶,直到新点在栈顶左侧(有点像单调栈的操作)

如下图所示,新点p18p18在向量p10p15p10p15的右边(当前前进方向),因此需要从栈中删除p10,p15p10,p15,让p8p8的下一个点为p18p18.重复这个过程,知道碰到最右边的pnpn,就求出了下凸包。

这里写图片描述
然后再反过来从pnpn开始再做一次,求出上凸包,合并起来就是完整的凸包了
这里写图片描述

struct Point{
    int x,y;
    Point(){}
    Point(int xx,int yy):x(xx),y(yy){}
    void read(){
        scanf("%d%d",&x,&y);
    }
    bool operator < (const Point &other)const{
        if(x == other.x)
            return y < other.y;
        return x < other.x;
    }
    Point operator - (const Point &other)const{
        return Point(x - other.x,y - other.y);
    }
};
Point p[400],ch[400];
int n;
double Cross(Point A,Point B){
    return A.x * B.y - A.y * B.x;
}
int ConvexHull(){
    sort(p,p+n);
    int cnt = 0;
    for(int i = 0; i < n; i++){
        while(cnt > 1 && Cross(ch[cnt-1] - ch[cnt-2],p[i] - ch[cnt-2]) <= 0) cnt--;
        ch[cnt++] = p[i];
    }
    int k = cnt;
    for(int i = n-2; i >= 0; i--){
        while(cnt > k && Cross(ch[cnt-1] - ch[cnt-2],p[i] - ch[cnt-2]) <= 0) cnt--;
        ch[cnt++] = p[i];
    }
    if(n > 1) cnt--;
    return cnt;
}

介绍完了凸包我们再来看看这道题怎么做呢?

需要用到最优三角剖分:


最优三角剖分:

对于一个n个顶点的凸多边形,有很多种方法可以对它进行三角剖分,即用n-3条互不相交的对角线把凸多边形分成n-2个三角形。为每个三角形规定一个权值函数w(i,j,k),求让所有三角形权和最大的方案。

定义dp[i][j]为子多边形i,i+1,….j-1,j(i < j)的最优值,则边i-j在最优解中一定对应一个三角形i-k-j,其中(i < k < j)那么同理,在i-k间也一定能找到一个最优值,k-j之间也可以找到一个最优值,一次类推

如图:
这里写图片描述
因此状态转移方程为

dp[i][j]=max(dp[i][j],dp[i][k]+dp[k][j]+w(i,j,k))dp[i][j]=max(dp[i][j],dp[i][k]+dp[k][j]+w(i,j,k))

时间复杂度O(n3)O(n3),问题的解为dp[0][n−1]dp[0][n−1]


那么对于这道题就很明确了

状态转移方程为:

dp[i][j]=min(dp[i][j],dp[i][k]+dp[k][j]+cost[i][k]+cost[k][j])dp[i][j]=min(dp[i][j],dp[i][k]+dp[k][j]+cost[i][k]+cost[k][j])

三重for循环枚举ijk,即可,区间dp

code:

#include <iostream>
#include <cstring>
#include <cstdio>
#include <algorithm>
using namespace std;
const int INF = 0x3f3f3f3f;
int m,f[400][400],dp[400][400];
struct Point{
    int x,y;
    Point(){}
    Point(int xx,int yy):x(xx),y(yy){}
    void read(){
        scanf("%d%d",&x,&y);
    }
    bool operator < (const Point &other)const{
        if(x == other.x)
            return y < other.y;
        return x < other.x;
    }
    Point operator - (const Point &other)const{
        return Point(x - other.x,y - other.y);
    }
};
Point p[400],ch[400];
int n;
double Cross(Point A,Point B){
    return A.x * B.y - A.y * B.x;
}
int ConvexHull(){
    sort(p,p+n);
    int cnt = 0;
    for(int i = 0; i < n; i++){
        while(cnt > 1 && Cross(ch[cnt-1] - ch[cnt-2],p[i] - ch[cnt-2]) <= 0) cnt--;
        ch[cnt++] = p[i];
    }
    int k = cnt;
    for(int i = n-2; i >= 0; i--){
        while(cnt > k && Cross(ch[cnt-1] - ch[cnt-2],p[i] - ch[cnt-2]) <= 0) cnt--;
        ch[cnt++] = p[i];
    }
    if(n > 1) cnt--;
    return cnt;
}
int calc(Point a,Point b){
    return (abs(a.x + b.x) * abs(a.y + b.y)) % m;
}
int main(){
    while(scanf("%d%d",&n,&m) != EOF){
        memset(p,0,sizeof(p));
        memset(ch,0,sizeof(ch));
        memset(f,0,sizeof(f));
        for(int i = 0; i < n; i++){
            p[i].read();
        }
        if(n == 3){
            puts("0");
            continue;
        }
        if(ConvexHull() < n){
            printf("I can't cut.\n");
        }
        else{
            for(int i = 0; i < n; i++){
                for(int j = i+2; j < n; j++){
                    f[i][j] = f[j][i] = calc(ch[i],ch[j]);
                }
            }
            for(int i = 0; i < n; i++){
                for(int j = 0; j < n; j++){
                    dp[i][j] = INF;
                }
                dp[i][(i+1)%n] = 0;
            }
            for(int i = n-3; i >= 0; i--){
                for(int j = i+2; j < n; j++){
                    for(int k = i+1; k < j; k++){
                        dp[i][j] = min(dp[i][j],dp[i][k]+dp[k][j]+f[i][k]+f[k][j]);
                    }
                }
            }
            printf("%d\n",dp[0][n-1]);
        }
    }
    return 0;
}
【Audio driver】深入解析mixer_paths.xml中的音频通路配置 本文深入解析了Android音频驱动开发中的核心配置文件mixer_paths.xml。文章以高通平台为例,详细阐述了音频通路(FE、BE、DSP、Device)的概念与连接逻辑,并通过实战案例拆解了扬声器与麦克风通路的配置方法、关键控件作用及调试技巧,是理解与定制Android音频系统的实用指南。 阅读详情

相关推荐

仿人型机械臂逆运动学避坑指南:当末端三关节平行时如何处理奇异点

本文深入探讨了6R仿人型机械臂在末三轴平行结构下的逆运动学求解策略,重点分析了运动学逆解中的奇异点问题及其处理方法。通过MATLAB实现展示了D-H参数建模、几何解析法求解流程以及奇异点规避策略,为工业机器人开发提供了实用的数值算法方案和工程优化技巧。

sss66的博客 882

ZOJ - 3537 Cake (凸包+经典区间dp)

题目链接:点击这里 题目大意: 给定 nnn 个点的坐标,如果这 nnn 个点能构成凸包,再用不相交的线来切这个凸包使得凸包只由三角形组成,切割代价是 cost(i,j)=∣xi+xj∣∗∣yi+yj∣cost(i, j) = |xi + xj| * |yi + yj| % pcost(i,j)=∣xi+xj∣∗∣yi+yj∣ ,求最少的切割费用。 题目分析: 先用把点排个序跑个凸包,如果是凸包再跑一下三角形划分的区间 dpdpdp ,其转移方程为:dp[i][j]=min(dp[i][j],dp[i][k

羊驼的博客 300

把“思考”塞进 1 KB:我用纯 C 语言给单片机手搓了一个微型 Transformer 推理引擎

摘要:本文探讨了在64KB SRAM的MCU(如STM32H743)上部署精简Transformer模型的技术方案。通过将6层Transformer压缩至1层(隐藏维度128)、4-bit KV-Cache量化等优化手段,实现了240KB Flash占用和59KB RAM峰值,推理延迟184ms(400MHz Cortex-M7),准确率96.1%。关键创新包括:手工优化矩阵乘(CMSIS-NN)、查表法Softmax/LayerNorm、权重按Tile重排提升Cache命中率(60%→94%)。

qq_74383080的博客 2922

ZOJ 3537-Cake(凸包+最优三角刨分+区间DP)

Cake Time Limit: 1 Second      Memory Limit: 32768 KB You want to hold a party. Here's a polygon-shaped cake on the table. You'd like to cut the cake into several triangle-shaped parts for th

信仰.的博客 811

【Linux】Petalinux使用QSPI FLASH引导启动

1. 预分配Flash空间使用Flash引导Petalinux做的系统,也有进阶的做法。部分图片和经验来源于网络,若有侵权麻烦联系我删除,主要是做笔记的时候忘记写来源了,做完笔记很久才写博客。1. 预分配Flash空间根据生成的bit文件大小估算BOOT.BIN文件的大小,为Flash大概分配四个分区:boot、bootenv、kernel、bootscr,分别存放BOOT.BIN文件、u-boot的环境变量、内核文件(image.ub/zImage/uImage等)、启动脚本boot.scr。

Tesseract_9527的博客 3374

第一届“龙信杯”电子数据取证竞赛Writeup

第一届“龙信杯”电子数据取证竞赛Writeup

toto的博客 1万+

ZOJ 3537-Cake(凸包+最优三角刨分+区间DP)

#include <stdio.h> #include <iostream> #include <string> #include <string.h> #include <algorithm> #include <math.h> using namespace std; struct node { int x,y; bo...

weixin_44879687的博客 216

pytorch-cifar100学习资料汇总 - 基于PyTorch的CIFAR-100图像分类实践

pytorch-cifar100是一个基于PyTorch实现CIFAR-100数据集图像分类的开源项目。该项目实现了多种经典的深度学习网络模型,如ResNet、DenseNet、VGG等,为开发者提供了在CIFAR-100数据集上进行图像分类实验的代码范例。pytorch-cifar100项目为我们提供了在CIFAR-100数据集上进行图像分类实验的完整代码实现。无论你是想要学习PyTorch的使用,还是研究不同网络模型在CIFAR-100上的表现,这个项目都是一个很好的起点。

helloaiworld的博客 1122

ZOJ 3537 Cake(凸包+区间DP)

思路:先判断是不是凸包,如果是的话,进行区间DP, dp[i][j] = min{dp[i][k] + dp[k][j] + cost[i][k] + cost[k[[j]} 代码: #include #include #include #include #include using namespace std; const int MAXN= 305; const int N = 3

Remilia's 626

S32K3xx系列DMA驱动实战:EB配置与Mcal接口应用全解析(含Adc硬件触发示例)

本文深入解析S32K3xx系列MCU的DMA驱动开发,涵盖EB工具配置与Mcal接口应用,特别包含ADC硬件触发示例。通过详细架构分析、实战配置步骤和工业级应用案例,帮助开发者掌握AUTOSAR环境下DMA高效数据传输技术,提升汽车电子和工业控制系统的性能。

weixin_29162439的博客 463

步进电机

步进电机

happygrilclh的博客 2140

zoj 3537 Cake 【凸包 + 区间dp】 【最优三角剖分】

Cake Time Limit: 1 Second      Memory Limit: 32768 KB You want to hold a party. Here's a polygon-shaped cake on the table. You'd like to cut the cake into several triangle-shaped parts for the

世界很大 1802

基于STM32L4XX的环境光传感器(LTR-303ALS-01)应用程序设计

/ 状态寄存器的位[2:0]表示数据状态,例如位2为1表示新数据就绪[citation:6]#define LTR303_REG_DATA_CH0_LOW 0x8D // CH0数据低字节。#define LTR303_REG_DATA_CH0_HIGH 0x8E // CH0数据高字节。#define LTR303_REG_DATA_CH1_LOW 0x8F // CH1数据低字节。#define LTR303_REG_DATA_CH1_HIGH 0x90 // CH1数据高字节。

myron6688的博客 405

zoj 3537 Cake (凸包 最优三角剖分)

题目链接这道题目是一道最优三角剖分的题目,其实也是一种区间dp里的一种应用,思路也很简单。这道题目还需要先是不是凸包,这里其实主要想记录一下凸包模板==#include <iostream> #include <cstdio> #include <cstring> #include <cmath> #include <algorithm> using namespace std; const dou

ciel_s的博客 503

温度PID控制PLC程序

温度PID稳定控制程序,适用于欧姆龙PLC,对其他PLC也具有很大参考价值

C# WinForm 基于DirectShow.dll编写的程序,可边预览边保存视频,音频和图片

基于微软的DirectShow.dll的二次开发1.自动识别连接的摄像头跟麦克风且可以对其进行选择(默认选中第一个)2.可录制wmv和avi两种格式的视频并且都带有音频,avi可以录制的分辨率和帧数进行选择,wmv默认进行了淸晰度优化如不喜欢可去除代码中有相关提示3.可在预览点开之后进行拍照,也可边录制视频边拍照4.添加了视频和音频的压缩功能(酌情使用)这次二次开发发现C#对DirectShow的相关信息太少,这次做完也不敢藏私共享出来,还望大家指正

ZOJ - 3537 Cake (凸包+区间DP+最优三角剖分)

Description You want to hold a party. Here's a polygon-shaped cake on the table. You'd like to cut the cake into several triangle-shaped parts for the invited comers. You have a knife to cut. The t

那些年 1917

迈瑞BS系列全自动生化分析仪LIS协议接口手册(内含HL7和ASTM)

迈瑞BS系列全自动生化分析仪LIS协议接口手册,内含HL7和ASTM)

zoj3537 Cake 【凸包+最优三角形划分】

判断输入的点能不能组成凸包(即所有点都要是凸包的顶点) 然后就是求最优三角形划分问题,也就是区间dp 感觉这种区间dp还是记忆化搜索写起来比较方便 记忆化搜索#include<bits/stdc++.h> using namespace std; const int inf=0x3fffffff; int top,s[10024];struct data { int x,y; } p[100

禅境花园 1057

ssm框架搭建

这个是一个在idea上成功跑起来的ssm框架项目,保存在这里方便以后使用直接下载

ZOJ-3537 Cake(区间dp+凸包最优三角形剖分)

A - Cake  ZOJ - 3537  题意:一块多边形,如果是凹多边形则直接输出“I can't cut.”,否则将他进行三角形剖分,每切一刀的花费是 |x1+x2|*|y1+y2|%p,x和y分别是点的坐标,问剖分的最小花费是多少 最优三角形剖分:对于一个n个顶点的凸多边形,可以用n-3条互不相交的对角线b把凸多边形分成n-2个三角形, 定义dp[i][j

十分残念的博客 630

ZOJ3537 解题报告及总结

题目意思就是 给你一个多边形,先判断是否是凸包,然后再划分成一个一个三角形,求最小代价,两点之间画一条线的最小代价为 abs(xi + xj) * abs(yi + yj) % p 才做的时候,想法是枚举划分的线,根据分治的思想,大的多边形拆成两个小多边形,然后记忆化,复杂度超高难写不说(因为要记录i节点的nxt节点编号,不停地变来变去),还不知道wa在哪。。 后来想了下,既然最后一定是一个一个的三

CQU_HYX的专栏 584

zoj3537(三角剖分->区间dp)

不说区间dp还真不造要往dp这边想。。 求完凸包每个多边形可以用2个端点表示,那么设d[i][j]为以ij为端点的凸多边形剖分完的最小代价 为了使转移看起来好看点这里就不把边ij算在内 d[i][j]=min{d[i][k]+d[k][j]+a[i][k]+a[k][j]}  k=i+1...j-1 这就变成了水dp了嘛。。 然后区间dp用记忆化搜索写起来十分舒服,比以前的写法要轻松

qkoqhh 315

ZOJ 3537

这道题,就是先判断是不是凸多边形。先求出凸包,如果所有点都在凸包上,那这些点就围成了凸多边形,反之则不是。然后就是分割凸多边形了,刚开始也想到了先确定一条边所在的三角形,从而确定分割的边。但边没选好,导致后续的状态很凌乱。后来看了相关的资料。先按一个顺序将多边形的n个点编号1--n。求f[1][n]先以边n--1为基准,确定其所在三角形,然后就得到了两个多边形。得到状态转移方程,f[1][n]=m

L&J COME!!!! 943

ZOJ-3537 Cake

凸包+区间DP第一次写区间DP的题,也是第一次写计算几何的题,找了一些模板用写完还是不太清楚区间DP具体是什么分类思路是借鉴这个人的:https://www.cnblogs.com/bhlsheji/p/4734765.html我写的是递归,他是递推#include&lt;iostream&gt; #include&lt;cstdio&gt; #include&lt;cstring&gt; #in...

wl16wzl的博客 314

ZOJ3537 Cake

ZOJ3537 Cake 传送门:http://acm.zju.edu.cn/onlinejudge/showProblem.do?problemCode=3537 题意: 给你几何形状的蛋糕,你需要按照顶点来切蛋糕,每次切蛋糕会产生一个贡献,\(val=cost_{i, j} *|x_i + x_j| * |y_i + y_j| % p\) 问你把蛋糕切成几个三角形所需要的最小花费 题解: 区间...

buerdepepeqi的优快云博客 266

ZOJ 3537 Cake 计算几何+区间dp

#include<bits/stdc++.h>using namespace std; typedef long long ll; const int inf = 0x3fffffff; struct node{ int x,y; }N[510],ans[510]; bool X(node a,node b,node c){ return (b.x-a.x)*(c.y-a.y)-(c

qq_33859479的博客 248

ZOJ 3537 简单凸包+DP

/* 简单学习了凸包,基本照着代码抄 凸包好像就是排序后跑一个polygon函数,就能得到一个凸包了 原理的话用平面直角坐标系的斜率理解凸包之后,图上的点被排序成顺时针排列的点 此时就是区间dp的思路了 */#include <cstdio> #include <cstring> #include <cstdlib> #include <cmath> #include

beihai2013 522

Zoj 3537 区间DP

转自:http://blog.youkuaiyun.com/woshi250hua/article/details/7824433 状态转移方程弄懂了,但是因为没有做计算几何,所以凸包的求解看不懂。。。。以后看。。。。先刷DP AC代码如下: #include #include #include #include using namespace std; #define MAX 0x3f3f3

马德里小铁匠的铁匠铺 757
上一篇: Yet Another Problem On a Subsequence(dp+组合数)
下一篇: Least common multiple (数论+完全背包)
Guuuuuu老师儿
博客等级 码龄9年 259粉丝 718原创
评论 2
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

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

抵扣说明:

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

余额充值