题目
思路
- 首先计算出区间内所有权重,最后按照权重排序即可。
- 计算权重时,如果计算过,那么直接用,如果没计算过,通过状态转移实现递归(如果为偶数,...;如果为奇数,...)
代码(c++)
class Solution {
public:
// 用于缓存权重的哈希表
std::unordered_map<int, int> weightCache;
// 计算权重的函数
int calculateWeight(int x) {
if (x == 1) return 0; // 基础条件
if (weightCache.count(x)) return weightCache[x]; // 如果缓存中存在,直接返回
// 递归计算权重
if (x % 2 == 0) {
weightCache[x] = 1 + calculateWeight(x / 2);
} else {
weightCache[x] = 1 + calculateWeight(3 * x + 1);
}
return weightCache[x];
}
// 主函数
int getKth(int lo, int hi, int k) {
std::vector<std::pair<int, int>> numbers;
// 计算区间内每个数字的权重
for (int i = lo; i <= hi; ++i) {
numbers.emplace_back(calculateWeight(i), i);
}
// 按权重排序,若权重相同按数字本身排序
std::sort(numbers.begin(), numbers.end(), [](const std::pair<int, int>& a, const std::pair<int, int>& b) {
return a.first == b.first ? a.second < b.second : a.first < b.first;
});
// 返回排序后第 k 个数字
return numbers[k - 1].second;
}
};
结果
End
其实dp应该也可以,dp是正推,通过dp[i]得到dp[2*i],dp[(i-1)/3],而dfs是反推。