现在有q个询问,每次询问想问你在[l,r]区间内,k进制表示中,k-1的数量最多的数是哪个数。比如当k=2时,9的二进制就是1001,那么他就有2个1.
输入描述:
第一行一个q,表示有q组询问。
接下来q行,每行三个整数k,l,r,分别表示进制数,查询的数字,以及查询的范围。
满足1<=q<=100000,2<=k<=16,1<=l<=r<=10^16
输出描述:
对于每组询问,输出答案。如果有多个答案,请输出最小的。
输入例子1:
1
8 1 100
输出例子1:
63
# Case 通过率 0%
# 把 [l, r] 区间内的数进行进制转换,之后计数,输出次数最多的那个数。
q = int(input())
nums, k, l, r = [], [], [], []
for i in range(q):
times = 0
nums = list(map(int, input().split()))
k = nums[0]
l = nums[1]
r = nums[2]
result = l
for j in range(l, r+1):
item = j
tmp = [j%k]
j = j // k
while (j):
tmp.append(j%k)
j = j // k
tmp = tmp[::-1]
# times = tmp.count(k-1) > times ? tmp.count(k-1) : times # 这是 C 语言中的三目运算符
result = item if tmp.count(k-1) > times else result # 这是 Python 中的三目运算符
times = tmp.count(k-1) # 问题出在这里,如果本次次数不大于上次次数,那么次数是不更新的,所以这条语句应该放在 if 语句里面。
print(result)
# 超时。Case 通过率 20%
q = int(input())
nums, k, l, r = [], [], [], []
for i in range(q):
times = 0
nums = list(map(int, input().split()))
k = nums[0]
l = nums[1]
r = nums[2]
result = l
for j in range(l, r+1):
item = j
tmp = [j%k]
j = j // k
while (j):
tmp.append(j%k)
j = j // k
tmp = tmp[::-1]
# times = tmp.count(k-1) > times ? tmp.count(k-1) : times
# result, times = item, tmp.count(k-1) if tmp.count(k-1) > times # 这个写法不对,我也不清楚为何。
if tmp.count(k-1) > times:
result = item
times = tmp.count(k-1)
print(result)
# 不需要数 k-1 的个数,因为输出的是满足条件的最小数,只需要从最低位开始变成 k-1,如果位数超出 lleft,那么在前面补 k-1
# 这是思路,我还没有改对,因为最开始进制转换 d2k 这个函数也是用数值计算的,而不是列表,最后造成超过十的进制全部出错,因为假如一个十六进制的数 12,会被拆成 1,2 两个数,所以进制转换时最好避免使用数学计算和字符串!
# 我还没改对,目前我不想在改了。。。。
q = int(input())
def k2d(num, k): # k 进制转化为十进制,输出为 int
res = 0
numstr = list(str(num))
l = len(numstr)
for i in range(l):
res += int(numstr[i]) * k**(l-i-1)
return res
def d2k(num, k): # 十进制转换为 k 进制,输出为 list
res = []
while not num:
res.append(num%k)
num = num // k
return res
def getnum(length, k): # 获得 length 长度的全部为 k-1 元素的数,输出为 list
res = []
for i in range(length):
res.append((k-1))
return res
def replacenum(List, n, k): # 将 List 最后 n 项变为 k-1,输出为 str
l = len(List)
res = List[: l-n]
for i in range(l-n, l):
res += str(k-1)
return res
def str2int(ListString): # 把字符串列表转换为对应的整数
res = 0
l = len(ListString)
for i in range(l):
res += int(ListString[i]) * 10**(l-i-1)
return res
def addnum(Str, n, k): # 在 Str 前补 n 个 k-1
res = str(k-1) * n + Str
return res
for i in range(q):
nums = list(map(int, input().split()))
k = nums[0]
l = nums[1]
r = nums[2]
l, r = d2k(l, k), d2k(r, k)
lleft, lright = len(list(str(l))), len(list(str(r)))
lstr, rstr = list(str(l)), list(str(r))
m = 1
while (m <= lleft):
tmp0 = str2int(replacenum(lstr, m, k))
if l <= str2int(replacenum(lstr, m, k)) <= r:
m += 1
else:
print(k2d(str2int(replacenum(lstr, m-1, k)), k))
break
m = lleft + 1
if tmp0 <= r:
n = 1
tmp1 = str2int(addnum(str(tmp0), n, k))
while(str2int(addnum(str(tmp0), n, k)) <= r):
n += 1
tmp2 = k2d(str2int(addnum(str(tmp0), n-1, k)), k)
print(k2d(str2int(addnum(str(tmp0), n-1, k)), k))
# 低位变 k-1 时,巧妙做法:假如百位数是5(八进制),那么变成七(八进制数百位)要加 2,对应十进制数要加 2*(8^2)
import java.util.ArrayList;
import java.util.Scanner;
public class Main {
public static long minNum(int k, long start, long end) {
ArrayList list = new ArrayList();
long tmp = start;
while (tmp != 0) {
long rest = tmp % k;
list.add((int) rest);
tmp = tmp / k;
}
long sum = 1;
for (int i = 0; i < list.size(); i++) {
long num = list.get(i);
num = k - 1 - num;
long size = (long) (num * sum);
if (start + size <= end) {
start = start + size;
} else {
return start;
}
sum = sum * k;
}
while (start < end) {
long size = (long) ((k - 1) * sum);
if (start + size <= end) {
start = start + size;
} else {
return start;
}
sum = sum * k;
}
return start;
}
public static void main(String[] args) {
Scanner in = new Scanner(System.in);
while (in.hasNextInt()) { //while循环没用 没有就可以
int time = in.nextInt();
for (int i = 0; i < time; i++) {
int k = in.nextInt();
long start = in.nextLong();
long end = in.nextLong();
System.out.println(minNum(k, start, end)); //这个真的值得学习 在每一次小循环中就输出一次答案 所以一定要编写函数
}
}
}
}
1. .count(item) 可以用于字符串,也可以用于列表,用来记字符串中或列表中 item 出现的次数。
即:string.count() 和 list.count()。
(参考:Python中的三目运算符(三元表达式))
2. 列表去重
nums = list(set(numsList))
3. 进制转换(尽量避免使用数学计算、字符串)
(1) 十进制转 k 进制
def d2k(num, k): # 十进制转换为 k 进制,输出为 list
res = []
while num:
res.append(num%k)
num = num // k
return res[::-1] # 倒序输出
(2) k进制转十进制
def k2d(num, k): # k 进制转化为十进制,输出为 int
res = 0
numstr = list(str(num))
l = len(numstr)
for i in range(l):
res += int(numstr[i]) * k**(l-i-1)
return res
4. 函数模块的合理使用!!!