C++ 花神游历各国

线段树,可是时间复杂度可能会爆掉,需要优化:

看代码:

#include<iostream>
#include<cstdio>
#include<cstring>
#include<cmath>
#define ll long long 
#define MAXN 100005
using namespace std;
int n,m;
ll s[4*MAXN];
bool mark[4*MAXN];
void up(int p){
	s[p]=s[p*2]+s[p*2+1];
	mark[p]=mark[p*2]&&mark[p*2+1];
	return ;
}
void build(int p,int l,int r){
	if(l==r){
		scanf("%lld",&s[p]);
		if(s[p]==1||s[p]==0)
			mark[p]=true;
		return ;
	}
	int m=l+r>>1;
	build(p*2,l,m);
	build(p*2+1,m+1,r);
	up(p);
	return ;
}
void update(int p,int l,int r,int x,int y){
	if(mark[p]) return ;
	if(r<x||l>y) return ;
	if(l==r){
		s[p]=sqrt(s[p]);
		if(s[p]==1||s[p]==0)
			mark[p]=true;
		return ;
	}
	int m=l+r>>1;
	update(p*2,l,m,x,y);
	update(p*2+1,m+1,r,x,y);
	up(p);
}
ll query_sum(int p,int l,int r,int x,int y){
	if(r<x||l>y) return 0LL;
	if(x<=l&&r<=y){
		return s[p];
	}
	int m=l+r>>1;
	ll ret=0;
	ret+=query_sum(p*2,l,m,x,y);
	ret+=query_sum(p*2+1,m+1,r,x,y);
	return ret;
}
int main(){
	scanf("%d",&n);
	build(1,1,n);
	scanf("%d",&m);
	for(int i=1,t,l,r;i<=m;i++){
		cin>>t>>l>>r;
		if(t==1){
			cout<<query_sum(1,1,n,l,r)<<"\n";
		}else{
			update(1,1,n,l,r);
		}
	}
	return 0;
}

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
C++中,骑士游历(Knight's Tour)是指在一个棋盘上,从某个起点出发,按照骑士(骑士移动规则为两步一跳,斜向前或后两格,然后向左或右一格)的方式访问每个格子,最终返回起点且不重复走过任何格子的一种经典问题。这个问题通常用回溯法或深度优先搜索(DFS)算法来解决,因为它涉及路径寻找和避免重复。 对于使用for循环来实现骑士游历,这通常不是首选方法,因为for循环更适合线性或等差序列的操作,而不适合这种动态生成路径的问题。但如果你想要创建一个简单的模拟,你可以使用嵌套循环来生成棋盘的每一个位置,并检查当前位置是否符合骑士的移动规则。 这里不是一个完整的骑士游历的for循环实现示例,因为这并不常见,但你可以用类似这样的方式来描述: ```cpp bool visited[BOARD_SIZE][BOARD_SIZE]; // 假设棋盘大小为BOARD_SIZE*BOARD_SIZE int startRow, startCol; // 起点坐标 // 初始化访问数组和开始位置 visited[startRow][startCol] = true; // 使用两层嵌套的for循环模拟骑士移动 for (int i = 0; i < BOARD_SIZE * 2 - 1; i++) { for (int j = 0; j < BOARD_SIZE * 2 - 1; j++) { if (i % 2 == 0 && j % 2 != 0) { // 模拟骑士向右两格 int newRow = startRow + i; int newCol = startCol + j; if (newRow >= 0 && newRow < BOARD_SIZE && newCol >= 0 && newCol < BOARD_SIZE && !visited[newRow][newCol]) { // 访问新位置并更新已访问 visited[newRow][newCol] = true; // 继续查找下一个可能的位置 continue; } } else if (i % 2 != 0 && j % 2 == 0) { // 向左两格 // ...类似代码... } // 添加其他两个方向的移动逻辑 } } // 如果到达最后一个位置并且没有返回,说明找到一个有效的游历路径 if (i == BOARD_SIZE * 2 - 2 && j == BOARD_SIZE * 2 - 2) { // 处理路径完成的逻辑 } ```

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值