面试题 01.01. 判定字符是否唯一;1160. 拼写单词;202. 快乐数;118. 杨辉三角;695. 岛屿的最大面积(并查集);面试题 01.07. 旋转矩阵

实现一个算法,确定一个字符串 s 的所有字符是否全都不同。

示例 1:

输入: s = "leetcode"
输出: false 


示例 2:

输入: s = "abc"
输出: true


限制:

    0 <= len(s) <= 100 
    如果你不使用额外的数据结构,会很加分。

class Solution {
public:
    bool isUnique(string astr){
        if(astr.size()<=1)return true;
        for(int i=0,tmp=0;i<astr.size();++i)
            if((tmp>>(astr[i]-'a'))&1)return false;
            else tmp|=1<<(astr[i]-'a');
        return true;
    }
    /*bool isUnique(string astr) {
        if(astr.size()<=1)return true;
        sort(astr.begin(),astr.end());
        for(int i=0;i<astr.size()-1;++i)
            if(astr[i]==astr[i+1])return false;
        return true;
    }*/
};

给你一份『词汇表』(字符串数组) words 和一张『字母表』(字符串) chars。

假如你可以用 chars 中的『字母』(字符)拼写出 words 中的某个『单词』(字符串),那么我们就认为你掌握了这个单词。

注意:每次拼写(指拼写词汇表中的一个单词)时,chars 中的每个字母都只能用一次。

返回词汇表 words 中你掌握的所有单词的 长度之和。

 

示例 1:

输入:words = ["cat","bt","hat","tree"], chars = "atach"
输出:6
解释: 
可以形成字符串 "cat" 和 "hat",所以答案是 3 + 3 = 6。


示例 2:

输入:words = ["hello","world","leetcode"], chars = "welldonehoneyr"
输出:10
解释:
可以形成字符串 "hello" 和 "world",所以答案是 5 + 5 = 10。


 

提示:


    1 <= words.length <= 1000
    1 <= words[i].length, chars.length <= 100
    所有字符串中都仅包含小写英文字母

class Solution {
public:
    int countCharacters(vector<string>& words, string chars) {
        unordered_map<char,int>mp;
        for(auto &i:chars)
            ++mp[i];
        int cnt=0;
        for(int i=0,j;i<words.size();++i){
            unordered_map<char,int>m;
            for(j=0;j<words[i].size();++j)
                if(mp.count(words[i][j])==0||++m[words[i][j]]>mp[words[i][j]])break;
            cnt+=j==words[i].size()?j:0;                
        }
        return cnt;
    }
};

编写一个算法来判断一个数 n 是不是快乐数。

「快乐数」定义为:对于一个正整数,每一次将该数替换为它每个位置上的数字的平方和,然后重复这个过程直到这个数变为 1,也可能是 无限循环 但始终变不到 1。如果 可以变为  1,那么这个数就是快乐数。

如果 n 是快乐数就返回 True ;不是,则返回 False 。

 

示例:

输入:19
输出:true
解释:
12 + 92 = 82
82 + 22 = 68
62 + 82 = 100
12 + 02 + 02 = 1

class Solution {
public:
    bool isHappy(int n) {
        int slow=n,fast=n;
        do{
            slow=helper(slow);
            fast=helper(helper(fast));
        }while(fast!=1&&slow!=fast);
        return fast==1;
    }
    int helper(int n){
        int res=0;
        while(n){
            res+=pow(n%10,2);
            n/=10;
        }
        return res;
    }
};

给定一个非负整数 numRows,生成杨辉三角的前 numRows 行。

在杨辉三角中,每个数是它左上方和右上方的数的和。

示例:

输入: 5
输出:
[
     [1],
    [1,1],
   [1,2,1],
  [1,3,3,1],
 [1,4,6,4,1]
]

class Solution {
public:
    vector<vector<int>> generate(int numRows) {
        if(numRows==0)return {};
        vector<vector<int>> res(numRows);
        for(int i=0;i<numRows;++i)
            res[i].resize(i+1,1);//
        for(int i=2;i<numRows;++i)
            for(int j=1;j<i;++j)
                res[i][j]=res[i-1][j-1]+res[i-1][j];
        return res;
    }
};

给定一个包含了一些 0 和 1 的非空二维数组 grid 。

一个 岛屿 是由一些相邻的 1 (代表土地) 构成的组合,这里的「相邻」要求两个 1 必须在水平或者竖直方向上相邻。你可以假设 grid 的四个边缘都被 0(代表水)包围着。

找到给定的二维数组中最大的岛屿面积。(如果没有岛屿,则返回面积为 0 。)

 

示例 1:

[[0,0,1,0,0,0,0,1,0,0,0,0,0],
 [0,0,0,0,0,0,0,1,1,1,0,0,0],
 [0,1,1,0,1,0,0,0,0,0,0,0,0],
 [0,1,0,0,1,1,0,0,1,0,1,0,0],
 [0,1,0,0,1,1,0,0,1,1,1,0,0],
 [0,0,0,0,0,0,0,0,0,0,1,0,0],
 [0,0,0,0,0,0,0,1,1,1,0,0,0],
 [0,0,0,0,0,0,0,1,1,0,0,0,0]]


对于上面这个给定矩阵应返回 6。注意答案不应该是 11 ,因为岛屿只能包含水平或垂直的四个方向的 1 。

示例 2:

[[0,0,0,0,0,0,0,0]]

对于上面这个给定的矩阵, 返回 0。

 

注意: 给定的矩阵grid 的长度和宽度都不超过 50。

class UnionFind{
    vector<int>parent,rank,size;
    int maxSize;
public:
    UnionFind(int m,int n,vector<vector<int>>& grid){
        int mn=m*n,tmp;
        parent.resize(mn,-1);
        rank.resize(mn,0);
        size.resize(mn,0);
        maxSize=0;
        for(int i=0;i<m;++i)
            for(int j=0;j<n;++j)
                if(grid[i][j]==1){
                    tmp=i*n+j;
                    parent[tmp]=tmp;
                    rank[tmp]=1;
                    size[tmp]=1;
                    maxSize=1;
                }
    }
    int Find(int x){
        return parent[x]==x?x:parent[x]=Find(parent[x]);
    }
    int getMaxSize(){
        return maxSize;
    }
    void Union(int a,int b){
        int fa=Find(a),fb=Find(b);
        if(fa==fb)return;
        if(rank[fa]<rank[fb]){
            parent[fa]=fb;
            size[fb]+=size[fa];
            maxSize=max(maxSize,size[fb]);
        }
        else {
            parent[fb]=fa;
            size[fa]+=size[fb];
            maxSize=max(maxSize,size[fa]);
        }
    }
};
class Solution {
    vector<int>dx={1,0,-1,0},dy={0,1,0,-1};
public:
    int maxAreaOfIsland(vector<vector<int>>& grid) {
        if(grid.size()==0||grid[0].size()==0)return 0;
        int m=grid.size(),n=grid[0].size();
        UnionFind *uf=new UnionFind(m,n,grid);
        for(int i=0,cur;i<m;++i)
            for(int j=0;j<n;++j)
                if(grid[i][j]==1){
                    grid[i][j]=0;
                    cur=i*n+j;
                    for(int k=0,tmp,x,y;k<4;++k){
                        x=i+dx[k],y=j+dy[k];
                        if(x<0||y<0||x==m||y==n||grid[x][y]==0)continue;
                        tmp=x*n+y;
                        uf->Union(cur,tmp);
                    }
                }
        return uf->getMaxSize();
    }
};

给你一幅由 N × N 矩阵表示的图像,其中每个像素的大小为 4 字节。请你设计一种算法,将图像旋转 90 度。

不占用额外内存空间能否做到?

 

示例 1:

给定 matrix = 
[
  [1,2,3],
  [4,5,6],
  [7,8,9]
],

原地旋转输入矩阵,使其变为:
[
  [7,4,1],
  [8,5,2],
  [9,6,3]
]


示例 2:

给定 matrix =
[
  [ 5, 1, 9,11],
  [ 2, 4, 8,10],
  [13, 3, 6, 7],
  [15,14,12,16]
], 

原地旋转输入矩阵,使其变为:
[
  [15,13, 2, 5],
  [14, 3, 4, 1],
  [12, 6, 8, 9],
  [16, 7,10,11]
]

class Solution {
/*上下相加都为n-1
上:(i,j)
下:(j,n-1-i)
左:(n-1-i,n-1-j)
右:(n-1-j,i)
*/
public:
    void rotate(vector<vector<int>>& matrix) {
        int n=matrix.size();
        if(n<=1)return;
        for(int i=0,endi=n>>1;i<endi;++i){
            for(int j=0,endj=(n+1)>>1;j<endj;++j){
                int tmp=matrix[i][j];
                matrix[i][j]=matrix[n-1-j][i];
                matrix[n-1-j][i]=matrix[n-1-i][n-1-j];
                matrix[n-1-i][n-1-j]=matrix[j][n-1-i];
                matrix[j][n-1-i]=tmp;
            }
        }
    }
};

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值