leetcode每日一题34

89.格雷编码

观察一下n不同时的格雷编码有什么特点

n=1 [0,1]

n=2 [0,1,3,2]

n=3 [0,1,3,2,6,7,5,4]

......

可以看到n=k时,编码数量是n=k-1的数量的一倍

同时n=k编码的前半部分和n=k-1一模一样

n=k编码的最后一位是2^k-1^

后半部分的编码是其对应的前半部分的对称的位置的数字+2^k-1^
如图可以看出原理,为了增加长度后,使得隔着中轴线相邻的第2^k-1^位和第2^k-1^+1位差一位,那么就要在新增加的位上由0变1(因为前半部分出现过在原有的位上是1的编码了)

也就是数字上增加了2^k-1^

至于其他的位,因为按照前面的编码放置1的顺序是唯一的,所以只要在最高位都填1,然后对称着顺序来就好了

因此代码为

cpp 复制代码
class Solution {
public:
    vector<int> grayCode(int n) {
        vector<int> gray;
        gray.push_back(0);
        gray.push_back(1);
        if(n==1)
            return gray;
        for(int i=2;i<=n;i++)
        {
            for(int j=pow(2,i-1)-1;j>=0;j--)
            {
                gray.push_back(gray[j]+pow(2,i-1));
            }
        }
        return gray;
    }
};

格雷编码有相当多的生成方法

还有一种,比如说G(i)=(i ^ (i >> 1))也就是G(i)=i^(i/2)
从这个图可以看出,如果二进制码字的第 i 位和 i+1 位(从右边开始数)相同,则对应的格雷码的第i位为0,否则为1(当i+1=n时,二进制码字的第n位被认为是0,即第n-1位不变)

cpp 复制代码
class Solution {
public:
    vector<int> grayCode(int n) {
        vector<int> gray;
        for(int i=0;i<pow(2,n);i++)
            gray.push_back(i^i>>1);
        return gray;
    }
};
相关推荐
Microsoft Word7 分钟前
c++基础语法
开发语言·c++·算法
天才在此20 分钟前
汽车加油行驶问题-动态规划算法(已在洛谷AC)
算法·动态规划
莫叫石榴姐1 小时前
数据科学与SQL:组距分组分析 | 区间分布问题
大数据·人工智能·sql·深度学习·算法·机器学习·数据挖掘
茶猫_2 小时前
力扣面试题 - 25 二进制数转字符串
c语言·算法·leetcode·职场和发展
肥猪猪爸4 小时前
使用卡尔曼滤波器估计pybullet中的机器人位置
数据结构·人工智能·python·算法·机器人·卡尔曼滤波·pybullet
readmancynn4 小时前
二分基本实现
数据结构·算法
萝卜兽编程4 小时前
优先级队列
c++·算法
盼海5 小时前
排序算法(四)--快速排序
数据结构·算法·排序算法
一直学习永不止步5 小时前
LeetCode题练习与总结:最长回文串--409
java·数据结构·算法·leetcode·字符串·贪心·哈希表
Rstln6 小时前
【DP】个人练习-Leetcode-2019. The Score of Students Solving Math Expression
算法·leetcode·职场和发展