当前位置: 首页 > news >正文

Kimi LeetCode 3533. 判断连接可整除性 C语言实现

这是 LeetCode 3533「判断连接可整除性」的 C 语言实现。题目要求找到字典序最小的排列,使得按顺序连接后的数能被 `k` 整除。

解题思路

本题使用状态压缩动态规划(Bitmask DP):

1. 预处理:先对 `nums` 排序,保证从小到大枚举,从而确保字典序最小。计算每个数的位数 `len[i]`,以及 `pow10[i] = 10^len[i] % k`
2. 状态定义:`dp[mask][mod]` 表示使用状态 `mask` 中的数(已选的数),当前余数为 `mod`,是否能形成合法连接
3. 状态转移:`newMod = (mod * pow10[i] + nums[i]) % k`
4. 路径重建:在 DP 后,按字典序从小到大尝试每个未使用的数,如果该路径能到达合法解,则选取该数

时间复杂度:O(n \cdot 2^n \cdot k),空间复杂度:O(2^n \cdot k)

C 语言代码

```c
#include <stdio.h>
#include <stdlib.h>
#include <string.h>

/**
* Note: The returned array must be malloced, assume caller calls free().
*/

// 比较函数,用于qsort排序
int cmp(const void *a, const void *b) {
return (*(int*)a - *(int*)b);
}

// 计算数字的位数
int numLen(int x) {
int len = 0;
while (x > 0) {
len++;
x /= 10;
}
return len;
}

// 快速幂: (base^exp) % mod
int modPow(int base, int exp, int mod) {
long long result = 1;
long long b = base % mod;
while (exp > 0) {
if (exp & 1) {
result = (result * b) % mod;
}
b = (b * b) % mod;
exp >>= 1;
}
return (int)result;
}

// 动态规划求解是否存在可行解
// dp[mask][mod]: -1=未计算, 0=false, 1=true
int solve(int *nums, int n, int k, int *pow10, int **dp, int mask, int mod) {
if (mask == (1 << n) - 1) {
return mod == 0 ? 1 : 0;
}
if (dp[mask][mod] != -1) {
return dp[mask][mod];
}

for (int i = 0; i < n; i++) {
if (!(mask & (1 << i))) {
int newMod = (int)((1LL * mod * pow10[i] + nums[i]) % k);
if (solve(nums, n, k, pow10, dp, mask | (1 << i), newMod)) {
dp[mask][mod] = 1;
return 1;
}
}
}

dp[mask][mod] = 0;
return 0;
}

// 重建答案路径
void reconstruct(int *nums, int n, int k, int *pow10, int **dp,
int mask, int mod, int *res, int *idx) {
if (mask == (1 << n) - 1) {
return;
}

for (int i = 0; i < n; i++) {
if (!(mask & (1 << i))) {
int newMod = (int)((1LL * mod * pow10[i] + nums[i]) % k);
if (solve(nums, n, k, pow10, dp, mask | (1 << i), newMod)) {
res[(*idx)++] = nums[i];
reconstruct(nums, n, k, pow10, dp, mask | (1 << i), newMod, res, idx);
return;
}
}
}
}

int* concatenatedDivisibility(int* nums, int numsSize, int k, int* returnSize) {
int n = numsSize;

// 排序,保证字典序最小
qsort(nums, n, sizeof(int), cmp);

// 预处理:计算每个数的位数和 10^len % k
int *pow10 = (int*)malloc(n * sizeof(int));
for (int i = 0; i < n; i++) {
int len = numLen(nums[i]);
pow10[i] = modPow(10, len, k);
}

// 初始化dp数组: dp[mask][mod]
int totalMask = 1 << n;
int **dp = (int**)malloc(totalMask * sizeof(int*));
for (int i = 0; i < totalMask; i++) {
dp[i] = (int*)malloc(k * sizeof(int));
for (int j = 0; j < k; j++) {
dp[i][j] = -1; // -1 表示未计算
}
}

// 检查是否存在解
int hasSolution = solve(nums, n, k, pow10, dp, 0, 0);

int *res = NULL;
if (hasSolution) {
res = (int*)malloc(n * sizeof(int));
int idx = 0;
reconstruct(nums, n, k, pow10, dp, 0, 0, res, &idx);
*returnSize = n;
} else {
res = (int*)malloc(sizeof(int));
*returnSize = 0;
}

// 释放内存
for (int i = 0; i < totalMask; i++) {
free(dp[i]);
}
free(dp);
free(pow10);

return res;
}
```

关键说明

要点 说明
排序 `qsort` 确保从小到大尝试,保证字典序最小
状态压缩 `mask` 范围 [0, 2^{13}),用位运算表示选了哪些数
取模运算 连接两个数时:`newMod = (oldMod * 10^len + num) % k`
记忆化 `dp[mask][mod]` 避免重复计算,-1/0/1 分别表示未计算/不可行/可行
路径重建 第二次遍历时按相同顺序选择第一个可行的数,保证字典序

示例验证

- `nums = [3,12,45], k = 5` → 输出 `[3,12,45]`(31245 % 5 = 0)
- `nums = [10,5], k = 10` → 输出 `[5,10]`(510 % 10 = 0)
- `nums = [1,2,3], k = 5` → 输出 `[]`(无解)

http://www.jsqmd.com/news/1175631/

相关文章:

  • 扩散模型训练效率优化挑战与Kohya_SS解决方案
  • 2026西安整装家装公司靠谱推荐:从口碑沉淀看三家本地高关注品牌 - 科技快讯
  • 医保防火墙替换后医保二维码测试有问题-最后定位医保路由器运行的OSPF路由协议未放通导致
  • 终极指南:如何安全修改艾尔登法环全平台游戏存档
  • FM5009G 600mA 锂电充电+3 档可调风量风扇IC
  • 2026年云南支持上门配送的亚克力板材批发源头工厂推荐及选择指南 - 热点速览
  • 2026年7月最新昆明泰格豪雅官方售后客服中心地址电话及服务网点分布 - 亨得利官方服务中心
  • Dify.AI语音交互架构深度解析:构建高效智能语音助手的终极指南
  • PrimoToon最佳实践:从数据挖掘资产到高质量渲染的完整流程
  • 为什么开发者都在寻找完全本地的图片格式转换解决方案?
  • 2026西安整装家装公司靠谱推荐:从口碑沉淀看三家本地高关注品牌 - 子柔传媒
  • iPhone 会议录音怎么转文字?2026 年 iOS 端 AI 录音工具推荐
  • 2026年武汉光谷口碑好的卫生间改造,哪家专业?答案即将揭晓! - 资讯快报
  • 为什么8倍性能提升的Node-read是您内容提取项目的明智选择
  • HarmonyOS 小游戏《对战五子棋》开发第40篇 - 五子棋项目总结和如何学习游戏开发
  • ScreenCoder:揭秘多智能体协同如何将UI截图转换为高质量HTML代码
  • 深度解析:自回归模型在生成式AI中的原理与实践指南
  • 【HarmonyOS】鸿蒙应用架构原则参考(HarmonyOS 5 企业级架构设计)
  • 冷暖色调总不达标,饱和度溢出频发,色域断层难修复——Midjourney专业级色彩一致性控制全链路拆解
  • 10|把一个 ESP32-S3 环境感知原型跑顺:从硬件、网页到后续改进
  • 从业务对象到可恢复编辑现场,完整理解 SAP Fiori 事务应用的 Draft 开发
  • 5分钟快速上手note-gen:跨平台AI智能笔记工具完全指南
  • 3步开启Kohya_ss Flux训练模式:新手也能轻松掌握的AI绘画微调指南
  • TLSFOWARD抓包工具 好用吗???
  • 2026惠州冰块批发工业降温冰块TOP排名榜:实测谁家降温最快? - 热点咨讯
  • 缓存命中率的艺术:深度解析Oracle Buffer Cache命中率提升策略
  • WeChatFerry:3个核心模块构建的微信机器人智能框架
  • 工业具身智能开启从技术验证向场景落地的进阶
  • Seed-VC零样本语音转换技术深度解析:扩散变换器架构与实时性能优化
  • 华为OD机试真题 新系统 2026-07-08 PythonJS 实现【迷宫相遇】