Confusing Problem

本文介绍了一道名为“ConfusingProblem”的题目,该题通过结合AC自动机构造状态与数位DP的方法进行解答。文章详细阐述了解题思路及代码实现,包括状态转移过程、AC自动机构建等关键步骤。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

北邮秋季赛  Confusing Problem


这个题比赛的时候没想出来,当时以为是数位dp,但是状态几乎都没法表示呀,单纯的以为  单独匹配A + 匹配B的 - 匹配A和B的,然后就没有然后了……

赛后看题解说是ac自动机+数位dp,猛然发现用ac自动机来构造状态时再合适不过了,题解是这样说的:


B 数位dp。

状态是dfs(i, m, s, e),i为当前做到前i位,m为是否已经匹配了两个串,s为走到自动机的节点s(或者kmp也能做),e为前i位是否是上限。


但是我敲了,仔细调试发现光有这些状态还是不行的,还要考虑到前缀是否为0,如果为0 ,那么当前i位可以为0,否则就必须从1开始

然后状态表示就是: dp[ pos ][ state] [ match ] [  zero ]  表示当前做到第i位,走到ac自动机state节点,目前是否匹配A或者B,前缀是否为0的个数


#include <cmath>
#include <cstdio>
#include <iostream>
#include <cstring>

using namespace std;

typedef long long ll;
const int NODE=150;
int chd[NODE][10],word[NODE],fail[NODE],sz;
int dig[50];
ll dp[50][NODE][2][2];

void ins(ll n)
{
    int pos=0;
    for(;n;n/=10) dig[pos++]=n%10;
    int p=0;
    for(int i=pos-1;i>=0;i--)
    {
        if(!chd[p][dig[i]])
        {
            memset(chd[sz],0,sizeof(chd[sz]));
            word[sz]=0;
            chd[p][dig[i]]=sz++;
        }
        p=chd[p][dig[i]];
    }
    word[p]=1;
}
int Que[NODE];
void ac()
{
    int *s=Que,*e=Que;
    for(int i=0;i<10;i++)
      if(chd[0][i]){
          *e++=chd[0][i];
          fail[chd[0][i]]=0;
      }
    while(s!=e)
    {
        int p=*s++;
        for(int i=0;i<10;i++)
          if(chd[p][i]){
             *e++=chd[p][i];
             fail[chd[p][i]]=chd[fail[p]][i];
             word[chd[p][i]]|=word[fail[chd[p][i]]];
          }else chd[p][i]=chd[fail[p]][i];
    }
}

ll dfs(int pos,int ok,int state,bool zero,bool doing)
{
    if(pos<0) return ok;
    if(!doing&&dp[pos][state][ok][zero]!=-1) return dp[pos][state][ok][zero];

    int end=doing?dig[pos]:9;
    ll ret=0;
    for(int i=zero?0:1;i<=end;i++)
    {
        int newstate=chd[state][i];
        ret+=dfs(pos-1,ok|word[newstate],newstate,zero&&!i,doing&&i==end);
    }
    if(!doing) dp[pos][state][ok][zero]=ret;
    return ret;
}

ll cal(ll n)
{
    int pos=0;
    for(;n;n/=10) dig[pos++]=n%10;
    return dfs(pos-1,0,0,1,1);
}

int main()
{
    ll L,R,A,B;
    int T;
    scanf("%d",&T);
    while(T--)
    {
        scanf("%lld%lld %lld%lld",&L,&R,&A,&B);
        sz=1;
        memset(chd[0],0,sizeof(chd[0]));
        ins(A);
        ins(B);
        ac();
        memset(dp,-1,sizeof(dp));
        printf("%lld\n",cal(R)-cal(L-1));
    }
    return 0;
}




翻译: Of course. After reviewing your Gradle files, it's clear the main problem is not a single error but a mix of structural issues, outdated practices, and critical typos. Your build script merges settings that should be in separate files and uses fragile methods that will cause constant problems. Here is a breakdown of the issues and a step-by-step guide to fix them. ----- ### \#\# 1. Critical Errors That Will Break the Build These issues need to be fixed first, as they will prevent Gradle from running correctly. #### **A. Typo in `targetSdk`** In your module's `build.gradle`, you have a typo. * **Problem:** `targetsdk 34` * **Fix:** It should be `targetSdk` (with a capital 'S'). <!-- end list --> ```groovy // In your module's build.gradle defaultConfig { minSdk 29 targetSdk 34 // FIX: Was 'targetsdk' } ``` #### **B. Typo in JaCoCo Configuration** In your `createOfflineTestCoverageReport` task, you have a typo in the word "configurations". * **Problem:** `classpath: configur3+ations.jacocoAnt.asPath` * **Fix:** It should be `configurations.jacocoAnt.asPath`. <!-- end list --> ```groovy // In your JaCoCo task ant.taskdef(name: 'report', classname: 'org.jacoco.ant.ReportTask', classpath: configurations.jacocoAnt.asPath) // FIX: Was 'configur3+ations' ``` ----- ### \#\# 2. Major Structural Problems Your project's build logic is incorrectly structured. You've mixed settings for the root project and the `model_base` module into one file. #### **A. Root Project and Module Logic are Mixed** You should have at least two `build.gradle` files: one in the project's root directory and one inside your `model_base` module. * **Project Root `build.gradle` or `build.gradle.kts`:** Should contain `buildscript` settings (like the Android Gradle Plugin version) and `allprojects` repository settings. It should **not** contain `apply plugin: 'com.android.library'` or Android-specific settings like `compileSdk`. * **Module `app/build.gradle` or `library/build.gradle.kts`:** Should contain `plugins { id 'com.android.library' }`, the `android { ... }` block, and the `dependencies { ... }` for that specific module. #### **B. Action Plan: Restructure Your Files** **Step 1: Create a `settings.gradle` file in your project root** (if you don't have one). It tells Gradle which modules are part of your project. ```groovy // settings.gradle include ':model_base' // include ':app' // if you have an app module ``` **Step 2: Clean up your Root `build.gradle` file.** It should only contain build-wide information. ```groovy // Project Root: build.gradle // The buildscript block is an older pattern, but if you keep it: buildscript { repositories { google() mavenCentral() } dependencies { // Use a consistent version for AGP classpath 'com.android.tools.build:gradle:8.1.0' // You don't need JaCoCo here; the plugin handles it. } } allprojects { repositories { google() mavenCentral() maven { url "https://jitpack.io" } } } ``` **Step 3: Create/Fix your Module `model_base/build.gradle` file.** This is where most of your current code should go. ```groovy // Module: model_base/build.gradle // Use the plugins block at the top plugins { id 'com.android.library' id 'jacoco' // Apply jacoco plugin here } android { namespace 'com.st.model_base' compileSdk 34 defaultConfig { minSdk 29 targetSdk 34 // Corrected typo } // ... your other android settings } dependencies { // ... your dependencies implementation 'androidx.appcompat:appcompat:1.6.1' // Updated version } // ... your JaCoCo tasks and configuration ``` ----- ### \#\# 3. Bad Practices and Recommendations These are issues that make your build slow, fragile, and hard to maintain. #### **A. Manual `bootstrapClasspath` Manipulation is Very Bad** Your use of `options.compilerArgs << '-Xbootclasspath/p:...'` and manually rebuilding the `bootstrapClasspath` to include `framework.jar` is an extremely fragile and outdated practice. * **Why it's bad:** It overrides the standard Android compile environment. It can break with any update to AGP, Gradle, or Java. It makes your build completely dependent on a local JAR file. * **Recommendation:** **Remove all three `gradle.projectsEvaluated` blocks.** Rely on the `compileSdk 34` to provide the Android APIs. If you absolutely need APIs not available in the public SDK, this approach is still not recommended and indicates a potential design flaw. #### **B. `dependsOn(clean)` is an Anti-Pattern** Your line `createOfflineTestCoverageReport.dependsOn(clean)` is very inefficient. * **Why it's bad:** It forces a complete project clean and recompile **every time** you want to generate a report. This will make your build process incredibly slow. * **Recommendation:** **Delete this line.** Gradle's tasks are designed to be incremental. #### **C. Redundant Configurations** You have multiple `tasks.withType(Test)` and `gradle.projectsEvaluated` blocks. This makes the script confusing. * **Recommendation:** Combine them into single blocks to avoid conflicts and make the logic clear. #### **D. Outdated Dependencies and Repositories** * **JCenter is Deprecated:** Remove `jcenter()` from your repositories. It was shut down years ago and can slow down your build as Gradle tries to connect to it. `mavenCentral()` has replaced it. * **Old AppCompat Library:** `androidx.appcompat:appcompat:1.4.1` is old for `compileSdk 34`. Update it to a more recent version like `1.6.1` to avoid potential incompatibilities.
最新发布
07-24
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值