关于kron, 我写过另一篇文章, 读者可以看一下, 熟悉一下kron的用法:
菡姐:使用kron来实现repmat, repelem的功能zhuanlan.zhihu.com题目的链接:
Project Euler: Problem 4, Palindromic numbersww2.mathworks.cn题目描述:
A palindromic number reads the same both ways. The largest palindrome made from the product of two 2-digit numbers is 9009 = 91 99.
Find the largest palindrome made from the product of numbers less than or equal to the input number.
Thank you to Project Euler Problem 4
意思很简单, 寻找一定范围内的两个数的乘积, 必须是回文数, 并且是最大的.
用数学语言表达大概就是:
max c = a*b
std:
1 <= a <= x
1 <= b <= x
c is palindromic number
回文数的定义是: 左右颠倒过来, 很原先一模一样, 即左右对称, 就像这篇文章的封面图一样.
先看我写的代码, 没有对比就没有伤害 o(╥﹏╥)o :
function ans = euler004(x)
v = x-99:x; % 这是v = 1:x的变形, 提高了搜索的下限, 目的为了节省内存和运算量.
M = unique(v'*v); % 利用矩阵乘法, 生成了乘积矩阵, 然后用unique去重, 以及压缩成向量
strM = string(M); % 变成string型, 目的是方便进行左右颠倒
M(find(reverse(strM) == strM, 1, 'last')); % 检验左右对称性
end
代码有注释, 就不多做解释了.
然后是最佳代码(size最小, 并且不是作弊代码, 比如使用regexp或者直接插入答案的)
function y = euler004(x)
for y = sort(kron(1:x,1:x),'descend')
if isequal(int2str(y),flip(int2str(y)))
return
end
end
分析:
1 使用了kron来构造"乘积向量".
这个是最大的亮点:
因为一般思路是利用矩阵乘法或者bsxfun来构造"乘积矩阵".
乘积向量相比乘积矩阵的优势是: 乘积矩阵在排序之前必须变形成向量, 多了一个步骤, 而kron直接就生成了向量, 相比之下, 少了一个步骤.
2 第二个亮点是for循环里面, 直接使用了该"乘积向量", 而不是在for循环里面生成索引.
for循环里面直接使用向量的做法, 相对来说是比较冷门技巧, 很多使用MATLAB多年的人都不知道.
举个例子说明:
例子1, 当V为行向量时, for循环每次取其中一个元素(标量).
V = [2, 5, 1.3];
cnt = 0;
for v = V
cnt = cnt + 1;
v
end
cnt
运行结果:
v =
2
v =
5
v =
1.3
cnt =
3
可以看到, 每次取一个元素, 并且循环了3次.
例子2, 当V为列向量时:
V = [2;5;1.3];
cnt = 0;
for v = V
cnt = cnt + 1;
v
end
cnt
运行结果:
v =
2
5
1.3
cnt =
1
运行结果与很多人预期的不同, 直接取了整个列向量, 因此, 也只需要循环一次.
例子3, 当V为矩阵时:
V = [1, 2;3, 4];
cnt = 0;
for v = V
cnt = cnt + 1;
v
end
cnt
运行结果:
v =
1
3
v =
2
4
cnt =
2
每次取其中一列, 有多少列就循环多少次.
从这三个例子中不难总结出规律:
MATLAB的for循环是以列为单位的.
3 使用了isequal来比较字符串.
也可以使用strcmp来比较字符串.
相比strcmp, isequal的使用范围更广.
4 使用了int2str, 也可以使用num2str
两者在整数情况下, 效果一样, 在有小数的情况下, int2str会先取整.
>> num2str(134)
ans =
'134'
>> int2str(134)
ans =
'134'
>> int2str(134.4)
ans =
'134'
>> num2str(134.4)
ans =
'134.4'
>> int2str(-134.4)
num2str(-134.4)
ans =
'-134'
ans =
'-134.4'
>> int2str(134.9)
num2str(134.9)
ans =
'135'
ans =
'134.9'
>> int2str(-134.9)
num2str(-134.9)
ans =
'-135'
ans =
'-134.9'
取整的方法明显为round.
这是MATLAB文档里面的解释:
chr = int2str(N) treats N as a matrix of integers and converts it to a character array that represents the integers. If N contains floating-point values, int2str rounds them before conversion.
创作不易, 请大家"素质三连": 点赞, 收藏, 分享.