关于 GDOI2025 GD-004 D2T1 的编译错误代码
/day2-GD-Senior-加密/answers/GD-004/move/move.cpp
#include <bits/stdc++.h>
#define ll long long
using namespace std;
inline int getchar(){
static char a[1<<20],*p=a,*q=a;
if(p==q) q=(p=a)+fread(a,1,1<<20,stdin);
return *p++;
}
inline int read(){
int x=0; int c=getchar();
for(;c<'0'||c>'9';c=getchar());
for(;c>='0'&&c<='9';c=getchar()) x=(x*10)+(c^48);
return x;
}
inline ll readll(){
ll x=0; int c=getchar();
for(;c<'0'||c>'9';c=getchar());
for(;c>='0'&&c<='9';c=getchar()) x=(x*10)+(c^48);
return x;
}
const int N=2e5+10;
ll arith(int l,int r){ return (r-l+1ll)*(l+r)>>1; }
int n;
int a[N],b[N]; ll tim[N];
int ord[N];
struct segt{
static const int M=N<<2;
int lef[M],rit[M],tag[M];
ll sum[M];
void psu(int p){
lef[p]=lef[p<<1];
rit[p]=rit[p<<1|1];
sum[p]=sum[p<<1]+sum[p<<1|1];
// printf("%d: lef %d rit %d sum %lld\n",p,lef[p],rit[p],sum[p]);
}
void psd(int p){
if(!tag[p]) return;
int mid=(lef[p]+rit[p])>>1;
lef[p<<1]=lef[p];
rit[p<<1]=mid;
sum[p<<1]=arith(lef[p],mid);
lef[p<<1|1]=mid+1;
rit[p<<1|1]=rit[p];
sum[p<<1|1]=arith(mid+1,rit[p]);
tag[p<<1]=tag[p<<1|1]=true;
tag[p]=false;
}
void build(int l,int r,int p){
tag[p]=0;
if(l==r) {
lef[p]=rit[p]=sum[p]=a[l];
return;
}
int mid=(l+r)>>1;
build(l,mid,p<<1);
build(mid+1,r,p<<1|1);
psu(p);
}
void push_left(int l,int r,int p,int x,int d){
if(r==x&&d-(r-l)<=lef[p]){
tag[p]=true;
rit[p]=d;
lef[p]=d-(r-l);
sum[p]=arith(lef[p],rit[p]);
return;
}
assert(l!=r);
psd(p);
int mid=(l+r)>>1;
if(x<=mid) push_left(l,mid,p<<1,x,d);
else{
push_left(mid+1,r,p<<1|1,x,d);
int plc=lef[p<<1|1]-1;
if(plc<rit[p<<1]) push_left(l,mid,p<<1,mid,plc);
}
psu(p);
}
void push_right(int l,int r,int p,int x,int d){
// printf("right %d %d %d %d %d\n",l,r,p,x,d);
if(l==x&&d+(r-l)>=rit[p]){
tag[p]=true;
lef[p]=d;
rit[p]=d+(r-l);
sum[p]=arith(lef[p],rit[p]);
return;
}
assert(l!=r);
psd(p);
int mid=(l+r)>>1;
if(x>mid) push_right(mid+1,r,p<<1|1,x,d);
else{
push_right(l,mid,p<<1,x,d);
int plc=rit[p<<1]+1;
if(plc>lef[p<<1|1]) push_right(mid+1,r,p<<1|1,mid+1,plc);
}
psu(p);
}
void build(){ build(1,n,1); }
// void dfs(int l,int r,int p){
// if(l==r){
// assert(lef[p]==rit[p]);
// printf("%d ",lef[p]);
// return ;
// }
// int mid=(l+r)>>1;
// psd(p);
// dfs(l,mid,p<<1); dfs(mid+1,r,p<<1|1);
// }
// void debug(){
// for(int i=1;i<=5;i++){
// printf("%d: lef %d rit %d sum %lld\n",i,lef[i],rit[i],sum[i]);
// }
// dfs(1,n,1);
// puts("");
// }
ll push_left(int x,int d){
ll before=sum[1];
push_left(1,n,1,x,d);
ll after=sum[1];
// printf("move LEF %d to %d cost %lld\n",x,d,before-after);
// debug();
return before-after;
}
ll push_right(int x,int d){
ll before=sum[1];
push_right(1,n,1,x,d);
ll after=sum[1];
// printf("move RIT %d to %d cost %lld\n",x,d,after-before);
// debug();
return after-before;
}
}T;
void solve(){
n=read();
for(int i=1;i<=n;i++){
a[i]=read(); b[i]=read(); tim[i]=readll();
ord[i]=i;
}
sort(ord+1,ord+n+1,[&](int x,int y){ return tim[x]<tim[y]; });
T.build();
ll rem=0;
for(int j=1;j<=n;j++){
int i=ord[j];
rem+=tim[i]-tim[ord[j-1]];
if(b[i]<a[i]) rem-=T.push_left(i,b[i]);
else rem-=T.push_right(i,b[i]);
if(rem<0){
puts("No");
return;
}
}
puts("Yes");
}
int main(){
freopen("move.in","r",stdin);
freopen("move.out","w",stdout);
int tc; read(); tc=read();
while(tc--){
// auto st=clock();
solve();
// auto ed=clock();
// cerr<<"CASE Time: "<<ed-st<<"\n";
}
}
这份代码在 g++-9 -std=c++14 -O2 的编译选项下会编译错误
move.cpp:4:12: error: ‘int getchar()’ redeclared inline without ‘gnu_inline’ attribute
4 | inline int getchar(){
| ^~~~~~~
In file included from /usr/include/stdio.h:976,
from /usr/include/c++/9/cstdio:42,
from /usr/include/x86_64-linux-gnu/c++/9/bits/stdc++.h:46,
from move.cpp:1:
/usr/include/x86_64-linux-gnu/bits/stdio.h:47:1: note: ‘int getchar()’ previously defined here
47 | getchar (void)
| ^~~~~~~
move.cpp: In function ‘int main()’:
move.cpp:155:9: warning: ignoring return value of ‘FILE* freopen(const char*, const char*, FILE*)’, declared with attribute warn_unused_result [-Wunused-result]
155 | freopen("move.in","r",stdin);
| ~~~~~~~^~~~~~~~~~~~~~~~~~~~~
move.cpp:156:9: warning: ignoring return value of ‘FILE* freopen(const char*, const char*, FILE*)’, declared with attribute warn_unused_result [-Wunused-result]
156 | freopen("move.out","w",stdout);
| ~~~~~~~^~~~~~~~~~~~~~~~~~~~~~~
这位选手定义了与标准库一样的函数名(inline int getchar()),本身是未定义行为,但更为致命的错误是 inline。去掉 inline 后可以编译通过,说明 inline 是问题所在。询问 AI 得到以下回答:
这个编译错误的原因主要是因为你重新定义了getchar函数并且使用了inline关键字,这与标准库中的getchar函数产生了冲突。以下是详细解释:
1. getchar函数的重定义问题
- 标准库中的
getchar函数:getchar是C标准库中的一个函数,用于从标准输入读取一个字符。它在<stdio.h>头文件中已经被定义。 - 你的代码中的
getchar函数:你在代码中重新定义了getchar函数,并且使用了inline关键字。在C++中,当你使用inline关键字重新定义一个已经在标准库中存在的函数时,编译器会报错,因为这会导致符号冲突。
2. inline关键字的问题
inline关键字的作用:inline关键字用于建议编译器将函数的调用替换为函数体,以减少函数调用的开销。但是,对于标准库中已经存在的函数,使用inline重新定义会导致冲突。- 解决方法:去掉
inline关键字,或者使用gnu_inline属性(这是GCC特有的属性)。不过,为了避免与标准库函数冲突,最好的方法是重命名你自己定义的函数,不要使用与标准库函数相同的名称。
本文来自博客园,作者:caijianhong,转载请注明原文链接:https://www.cnblogs.com/caijianhong/p/18771088
浙公网安备 33010602011771号