AGC012 - E: Camel and Oases

本文探讨了使用状压动态规划解决一个骆驼遍历绿洲的问题,通过预处理和多层线段选择策略,实现了高效遍历算法。分析了时间复杂度并提供了详细的代码实现。

原题链接

题意简述

沙漠中有n(n2×105)个排成一条直线的绿洲,一头储水量为V(V2×105)的骆驼。
骆驼有两个操作:

  • 走到距离在V以内的一个绿洲。
  • 飞到任意一个绿洲,但V减少一半。V=0时不能飞。

问骆驼依次从每个绿洲出发,能否一次性遍历所有绿洲。

分析

首先预处理出 V=V0 时哪些绿洲之间是可以随便走的,对于每个V0扫一遍即可。时间复杂度为O(nlog2V)

每飞一次相当于下一层。题目转化成钦定第一条线段,然后从每一层选一条线段,问能否覆盖整个区间。
万万没想到,这道题居然是状压DP!!!

s中的后起第i位为1表示从第i层选出了一条线段。
f1[s]表示状态s时从1起向右最远能延伸到哪,f2[s]表示状态s时从n起向左最远能延伸到哪。
f1[s]=max(f1[s],upFind(f1[s0]))
f2[s]=min(f2[s],lowFind(f2[s0]1))
意义是从s0加上一条线段能延伸到哪。这个转移方程和我的写法有关,具体看代码。
时间复杂度O(log2Vlog2n2log2V+1)=O(Vlog2nlog2V)

检查答案时,对于第一层的每一条线段,寻找是否存在s,使得f1[s],f2[Us1]和该线段覆盖整个区间。表示用状态s这些线段尽可能扩展左半部分,用剩下的线段(不包括第一层)尽可能扩展右半部分,再加上第一层的这条线段。
最大时间复杂度O(n2log2V)=O(nV),GG ╮(╯﹏╰)╭
但实际上,第一层的线段条数是不能超过log2V+1的。因为飞log2V+1次后V0=0,并且下一层的条数比上一层只多不少,要是第一层就超过log2V+1那么不可能遍历所有绿洲。
所以最大时间复杂度为O(Vlog2V)

总时间复杂度最大为O(nlog2V+Vlog2nlog2V)

实现

a[i][j]记录第i层的第j条线段的右端点。特别地,a[i][0]记录第i层线段的条数。
upFind(x)找出第一个严格大于x的右端点。这个右端点所在的区间一定能延伸当前的f1
lowFind(x1)找出第一个严格小于x-1的右端点。这个右端点的下一个区间一定能延伸当前的f2。如果写lowFind(x),要是找到x-1的话,说明有一段以x-1为右端点的区间以及一段以x为左端点的区间。这时候明明可以加入前者,实际上却加入了后者,导致问题。

代码

//Camel and Oases
#include <cstdio>
#include <cstring>
#include <algorithm>
using namespace std;
typedef long long lint;
int const N=2e5+10;
int const S=1<<19;
int n,V;
lint d[N];
int logV,a[25][N];
int U,f1[S],f2[S];
int upFind(int a[],int x)
{
    int L=1,R=a[0];
    while(L<R-1)
    {
        int mid=(L+R)>>1;
        if(a[mid]<=x) L=mid+1;
        if(a[mid]>x) R=mid;
    }
    if(a[L]>x) return a[L];
    else return a[R];
}
int lowFind(int a[],int x)
{
    int L=1,R=a[0];
    while(L<R-1)
    {
        int mid=(L+R)>>1;
        if(a[mid]<x) L=mid;
        if(a[mid]>=x) R=mid-1;
    }
    if(a[R]<x) return a[R]+1;
    else return a[L]+1;
}
int main()
{
    scanf("%d%d",&n,&V);
    logV=0;
    while((1<<logV)<=V) logV++;
    logV++;
    for(int i=1;i<=n;i++) scanf("%lld",&d[i]),d[i-1]=d[i]-d[i-1];
    d[n]=0;
    for(int i=1;i<=logV;i++)
    {
        a[i][0]=1;
        for(int j=1;j<=n;j++)
        {
            a[i][a[i][0]]=j;
            if(d[j]>(V>>(i-1))) a[i][0]++;
        }
    }
    if(a[1][0]>logV)
    {
        for(int i=1;i<=n;i++) printf("Impossible\n");
        return 0;
    }
    U=(1<<logV)-1;
    for(int s=0;s<=U;s++) f1[s]=0,f2[s]=n+1;
    for(int s=0;s<=U;s+=2)
        for(int i=2;i<=logV;i++)
        {
            int s0=1<<(i-1);
            if(s&s0) continue;
            f1[s|s0]=max(f1[s|s0],upFind(a[i],f1[s]));
            f2[s|s0]=min(f2[s|s0],lowFind(a[i],f2[s]-1));
        }
    for(int i=1;i<=a[1][0];i++)
    {
        bool f=false;
        int fr=a[1][i-1]+1,to=a[1][i];
        if(i==1) fr=1;
        for(int s=0;s<=U&&!f;s+=2)
            if(fr<=f1[s]+1 && f2[U-s-1]-1<=to) f=true;
        if(f) for(int j=fr;j<=to;j++) printf("Possible\n");
        else for(int j=fr;j<=to;j++) printf("Impossible\n");
    }
    return 0;
}

注意

  • 因为最多飞log2V+1次,所以全集状态U=2log2V+11,体现在题目中为219,而不是218
  • a[i][0]做他用,有些地方写的可能会麻烦一些。

转载于:https://www.cnblogs.com/VisJiao/p/8485770.html

<think>我们正在配置MyBatis-Plus,需要设置`mapper-locations`和`global-config`参数。这两个参数分别用于指定Mapper XML文件的位置和全局配置。 根据引用[1]和引用[2]中的信息,我们可以这样配置: 1. **mapper-locations**:用于指定MyBatis Mapper XML文件的位置。在Spring Boot项目中,我们通常在application.yml(或application.properties)中进行配置。 2. **global-config**:用于设置MyBatis-Plus的全局配置,例如表前缀、主键生成策略等。 下面是一个配置示例(以application.yml为例): ```yaml mybatis-plus: # 配置Mapper XML文件的位置 mapper-locations: classpath*:mapper/**/*.xml global-config: # 全局配置设置 db-config: # 全局表前缀 table-prefix: tbl_ # 全局主键类型 id-type: auto ``` 解释: - `mapper-locations: classpath*:mapper/**/*.xml`:表示在classpath路径下(包括jar文件内)的所有mapper目录及其子目录中查找所有以.xml结尾的文件作为Mapper XML文件。 - `global-config.db-config.table-prefix: tbl_`:设置全局表前缀为`tbl_`,这样在实体类上不需要使用`@TableName`指定表名时,会自动将实体类名转换为小写并在前面加上`tbl_`作为表名。例如,实体类`User`对应的表名是`tbl_user`。 - `global-config.db-config.id-type: auto`:设置主键生成策略为数据库自增(如MySQL的AUTO_INCREMENT)。 另外,引用[3]提醒我们,在配置中如果使用占位符(如`${...}`),需要确保该占位符在配置文件中已经定义,并且注意配置文件加载顺序。但在这个配置中,我们没有使用占位符,所以不用担心。 如果使用application.properties配置,则如下: ```properties # Mapper XML文件位置 mybatis-plus.mapper-locations=classpath*:mapper/**/*.xml # 全局配置 mybatis-plus.global-config.db-config.table-prefix=tbl_ mybatis-plus.global-config.db-config.id-type=auto ``` 注意:在配置`id-type`时,常用的值有: - `auto`:数据库自增 - `none`:无状态,该类型为未设置主键类型(跟随全局) - `input`:用户输入ID - `assign_id`:分配ID(主键类型为Number(Long和Integer)或String),使用接口`IdentifierGenerator`的方法`nextId`(默认实现类为`DefaultIdentifierGenerator`雪花算法) - `assign_uuid`:分配UUID(主键类型为String) 请根据实际需求选择。 最后,确保你的Mapper接口被正确扫描,通常使用`@MapperScan`注解在启动类上指定Mapper接口所在的包,例如: ```java @SpringBootApplication @MapperScan("com.example.mapper") public class Application { public static void main(String[] args) { SpringApplication.run(Application.class, args); } } ``` 这样,MyBatis-Plus就能找到Mapper接口和对应的XML文件,并应用全局配置。 §§相关问题§§ 1. MyBatis-Plus中如何配置多个mapper-locations路径? 2. global-config除了表前缀和主键类型,还有哪些常用配置? 3. 如何为不同的表设置不同的主键生成策略? 4. 在MyBatis-Plus中,如何自定义ID生成器?</think>### MyBatis-Plus 配置参数详解 #### 1. **mapper-locations 参数配置** **作用**:指定 MyBatis Mapper XML 文件的路径位置,支持通配符匹配多个文件。 **配置示例**(YAML 格式): ```yaml mybatis-plus: mapper-locations: classpath*:mapper/**/*.xml ``` **说明**: - `classpath*:`:从所有类路径(包括依赖的 JAR 包)中搜索 - `mapper/**/*.xml`:匹配 `mapper` 目录下所有子目录的 `.xml` 文件 - 支持多个路径,用逗号分隔(如:`classpath:mapper1/*.xml, classpath:mapper2/*.xml`) #### 2. **global-config 参数配置** **作用**:配置全局策略,包含数据库表前缀、主键生成策略等。 **配置示例**(YAML 格式): ```yaml mybatis-plus: global-config: db-config: table-prefix: tbl_ # 全局表前缀 id-type: auto # 主键策略(auto: 数据库自增) logic-delete-field: deleted # 逻辑删除字段名 logic-delete-value: 1 # 删除状态值 logic-not-delete-value: 0 # 未删除状态值 ``` **关键子配置说明**: | 参数 | 说明 | 可选值 | |------------------------|----------------------------------------------------------------------|---------------------------------| | `table-prefix` | 自动给所有表名添加前缀(如 `user` → `tbl_user`) | 任意字符串 | | `id-type` | 主键生成策略 | `auto`(自增),`assign_id`(雪花ID)| | `logic-delete-field` | 逻辑删除字段名(需在表中存在) | 如 `is_deleted` | | `logic-delete-value` | 删除状态值 | 数字/字符串 | | `logic-not-delete-value`| 未删除状态值 | 数字/字符串 | #### 3. **完整配置示例** ```yaml mybatis-plus: mapper-locations: classpath*:com/example/mapper/**/*.xml global-config: db-config: table-prefix: sys_ id-type: assign_id logic-delete-field: is_deleted logic-delete-value: 1 logic-not-delete-value: 0 configuration: map-underscore-to-camel-case: true # 开启驼峰命名转换 ``` #### 4. **注意事项** 1. **路径通配符规则**: - `*` 匹配单层目录 - `**` 匹配多层目录 - 示例:`classpath*:mappers/**/postgresql/*Mapper.xml` 2. **优先级规则**: - 实体类注解(如 `@TableName`)> 全局配置 > 数据库表名 - 例如:若实体类有 `@TableName("user")`,则忽略全局 `table-prefix` 3. **逻辑删除配置**: ```java @TableLogic private Integer isDeleted; // 需与global-config中的字段名一致 ``` 4. **多模块项目**: ```yaml mapper-locations: - classpath*:module1/mapper/*.xml - classpath*:module2/mapper/**/*.xml ``` [^1]: 关于 MyBatis-Plus 的基本配置路径定义,详见官方文档 [^2]: 全局表前缀配置的实际应用效果示例
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值