首页 > 试题广场 >

扑克牌顺子

[编程题]扑克牌顺子
  • 热度指数:479835 时间限制:C/C++ 1秒,其他语言2秒 空间限制:C/C++ 256M,其他语言512M
  • 算法知识视频讲解
现在有2副扑克牌,从扑克牌中随机五张扑克牌,我们需要来判断一下是不是顺子。
有如下规则:
1. A为1,J为11,Q为12,K为13,A不能视为14
2. 大、小王为 0,0可以看作任意牌
3. 如果给出的五张牌能组成顺子(即这五张牌是连续的)就输出true,否则就输出false。
4.数据保证每组5个数字,每组最多含有4个零,数组的数取值为 [0, 13]

要求:空间复杂度 ,时间复杂度 ,本题也有时间复杂度 的解法

输入描述:
输入五张扑克牌的值


输出描述:
五张扑克牌能否组成顺子。
示例1

输入

[6,0,2,0,4]

输出

true

说明

中间的两个0一个看作3,一个看作5 。即:[6,3,2,5,4]
这样这五张牌在[2,6]区间连续,输出true 
示例2

输入

[0,3,2,6,4]

输出

true
示例3

输入

[1,0,0,1,0]

输出

false
示例4

输入

[13,12,11,0,1]

输出

false
# -*- coding:utf-8 -*-
class Solution:
    def IsContinuous(self, numbers):
        # write code here
        res = [i for i in numbers if i]
        if len(set(res)) != len(res) or (max(res) - min(res)) >= 5:
            return False
        return True
发表于 2021-05-21 13:39:56 回复(0)
# -*- coding:utf-8 -*-
class Solution:
    def IsContinuous(self, numbers):
        # write code here
        numbers.sort()         # 扑克牌先排序
        zero_num = numbers.count(0) # 找出大小王,也就0的张数
        if zero_num == 4:     #如果四个0,则肯定可以组成顺子
            return True
        for index in range(5):   # 去除所有的0
            if numbers[index]:
                numbers = numbers[index:]
                break
        if len(numbers) - len(set(numbers)): # 如果包含重复数字,则不可能组成顺子
            return False
        if max(numbers) - min(numbers) <= 4:  # 如果最大牌减最小牌不超过4,则肯定可以组成顺子
            return True
        return False
发表于 2021-05-19 22:23:13 回复(0)
# -*- coding:utf-8 -*-
class Solution:
    def IsContinuous(self, numbers):
        # write code here
        if len(numbers)!=5:
            return False
        num_0=numbers.count(0)
        dif=0
        numbers.sort()
        n=len(numbers)
        for i in range(n-1):
            if numbers[i]!=0:
                if numbers[i]==numbers[i+1]:
                    return False
                else:
                    dif+=numbers[i+1]-numbers[i]-1
        if dif>num_0:
            return False
        else: return True

发表于 2021-05-05 01:24:53 回复(0)
# -*- coding:utf-8 -*-
class Solution:
    def IsContinuous(self, numbers):
        # write code here
        numbers = sorted(numbers)
        l_0 = 0
        for i in range(len(numbers)):    #统计0的个数
            if numbers[i] == 0:
                l_0 += 1
            else:
                l_n = len(numbers)-l_0
                break
        if l_0 >= 4:    #0的数量大于等于4时,必定为顺
            return True
        else:
            numbers = numbers[l_0:]    #留下非0牌
            for i in range(len(numbers)):
                if numbers[i] == numbers[i-1]:    #非0牌出现重复时直接False
                    return False
            #因为牌数固定为5,如果可能为顺子的话,最大值最小值之差不能大于4
            return (max(numbers)-min(numbers)) <= 4
发表于 2021-04-21 21:22:47 回复(0)
Python 左边对齐,一个一个看是否相等,不相等就补0,直到0用完,看后面的是否相等。
# -*- coding:utf-8 -*-
class Solution:
    def IsContinuous(self, numbers):
        # write code here
        if len(numbers)==0:
            return False
        # 扑克牌去掉0,排序
        temp = []
        for x in numbers:
            if x>0:
                temp.append(x)
        temp.sort()
        # 5-len(temp)就是大小鬼的数量,zero=0~4,len(temp)=1~5
        zero = 5-len(temp)
        if zero==4:
            return True
        else:
            # zero=0~3,len(temp)=2~5
            if temp[-1]-temp[0]>5:
                return False
            else:
                # temp2 是目标的顺子,以temp[0]为起点
                temp2 = []
                for i in range(5):
                    temp2.append(temp[0]+i)
                idx = 0
                while True:#idx<len(temp):
                    if temp2[idx]==temp[idx]:
                        idx+=1
                    else:
                        if zero:
                            temp.insert(idx,temp2[idx])
                            zero -=1
                        else:
                            return False
                    if idx==5:
                        return True


发表于 2021-04-18 00:43:11 回复(0)
  1. 将列表排序,统计元素为0的个数temp
  2. 如果列表为空,返回False;
  3. 逐个遍历所有元素,如果元素为0,或者相邻元素之差为1,则跳过,进入下一步;
  4. 如果相邻元素相等,返回False;
  5. 如果相邻元素之差>1,则用0的个数去补充缺失的元素;
  6. 如果0的个数为负数,返回False;
  7. 循环结束,返回True.
# -*- coding:utf-8 -*-
class Solution:
    def IsContinuous(self, numbers):
        numbers.sort()
        temp = numbers.count(0)
        if not numbers:
            return False
        for i in range(len(numbers)-1):
            if numbers[i] == 0 or numbers[i+1] - numbers[i] == 1:
                continue
            if numbers[i] == numbers[i+1]:
                return False
            if numbers[i+1] - numbers[i] > 1:
                temp -= (numbers[i+1] - numbers[i] - 1)
            if temp < 0:
                return False
        return True




编辑于 2021-03-31 20:21:52 回复(0)

python解法:
解法1:排序之后数组中除了0的其他数字差值要在5以内,且不能有重复数字;

class Solution:
    def IsContinuous(self, numbers):
        if len(numbers) == 0:
            return False
        n = len(numbers)
        numbers = sorted(numbers)
        # 统计0的个数
        m = numbers.count(0)
#         for i in range(m,n-1):# 循环体内的m和n变化,并不会影响i的变化;
        for i in range(m,len(numbers)-1):
            # 1.numbers[i+1] - numbers[i] == 0看是否有重复元素;
            # 2.numbers[i+1] - numbers[i] >= n 排序之后数组中除了0的其他数字差值要在5以内;
            if numbers[i+1] - numbers[i] == 0 or numbers[i+1] - numbers[i] >= n:
                return False
            elif numbers[i+1] - numbers[i] < n:
                n -= numbers[i+1] - numbers[i]
        return True

解法2:统计0的个数,计算数组最大值和最小值(除了0)的差值,
若0的个数 <= 差值,则输出false,否则输出true,还要考虑不能有重复的数字;

class Solution:
    def IsContinuous(self, numbers):
        if len(numbers) == 0:
            return False
        n = len(numbers)
        numbers = sorted(numbers)
        # 统计0的个数
        m = numbers.count(0)
        for i in range(m,n-1):
            # 1.numbers[i+1] - numbers[i] == 0看是否有重复元素;
            # 2.numbers[i+1] - numbers[i] > m 看相邻两数的差值是否小于0的个数,因为是全部相邻两数的差值,其实就是最大值与最小值的差值与0的个数的比较;
            if numbers[i+1] - numbers[i] == 0 or numbers[i+1] - numbers[i] - 1 > m:
                return False
            elif numbers[i+1] - numbers[i] - 1 <= m:
                m -= numbers[i+1] - numbers[i] - 1
        return True
发表于 2021-02-19 15:42:22 回复(0)
class Solution:
    def IsContinuous(self, numbers):
        # write code here
        if len(numbers)>0:
            a=numbers.count(0)
            c=sorted(numbers)[a:]
            if len(c)==len(set(c)):
                if c[-1]-c[0]<=4:
                    return True
                else:
                    return False
            else:
                return False
        else:
            return False

发表于 2020-11-27 18:42:24 回复(0)
不知道为啥有问题:
# -*- coding:utf-8 -*-
class Solution:
    def IsContinuous(self,numbers):
        # write code here
        count_zero = 0
        minimum = 0
        maximum = 0
        for i in numbers:
            if i == 0:
                count_zero += 1
            elif i < minimum or minimum == 0:
                minimum = i
            elif i > maximum or maximum == 0:
                maximum = i
            else:
                continue
        if (maximum-minimum+1) <= len(numbers):
            return "true"
        else:
            return "false"


编辑于 2020-10-29 00:17:28 回复(0)
# -*- coding:utf-8 -*-
class Solution:
    def IsContinuous(self, numbers):
        if not numbers:
            return False
        numbers.sort()
        n = numbers.count(0)
        for j in range(n):
            numbers.remove(0)
        if max(numbers)-min(numbers)>4:
            return False
        for i in range(len(numbers)-1):
            if numbers[i+1]-numbers[i]!=1:
                if n==0&nbs***bsp;numbers[i+1]==numbers[i]:
                    return False
                else:
                    n-=1
        return True

编辑于 2020-10-20 15:16:55 回复(0)
class Solution:
    def IsContinuous(self, numbers):
        if len(numbers) == 0:
            return False
        numbers.sort()
        wang = 0
        for i in range(4):
            if numbers[i] == 0:
                wang += 1
                continue
            while numbers[i] + 1 != numbers[i + 1]:
                if wang > 0:
                    numbers[i] += 1
                    wang -= 1
                else:
                    return False
        return True
发表于 2020-08-15 23:17:17 回复(0)
# -*- coding:utf-8 -*-
class Solution:
    def IsContinuous(self, numbers):
        # write code here
        #1、如果输入为空,返回false
        #2、除了王的任何某个特定数值的牌出现两张或者更多,那么一定凑不齐顺子。
        #思路,先统计王的数量,再把牌排序,如果后面一个数比前面一个数大于1以上,
        #那么中间的差值就必须用王来补了。看王的数量够不够,如果够就返回true,否则返回false。
        if not numbers:
            return False
        numbers.sort()#其实这里也将numbers由小到大排序了
        zeroNum = numbers.count(0)
        for index,value in enumerate(numbers[:-1]):
            if value != 0:
                if value == numbers[index+1]:
                    return False
                zeroNum = zeroNum -(numbers[index+1] - value)+1#前面排序了,所以括号里面肯定为正
                if zeroNum < 0:
                    return False
        return True

发表于 2020-07-26 21:03:06 回复(0)
# -*- coding:utf-8 -*-
class Solution:
    def IsContinuous(self, numbers):
        # write code here
        if not numbers:
            return False
        numbers.sort()
        new_list = [i for i in numbers if i > 0]
        n = len(new_list)
        if n == 1:
            return True
        for i in range(n-1):
            if new_list[i+1] - new_list[i] == 0:
                return False
        num = max(new_list) - min(new_list)
        if num <= 4:
            return True
        return False
解题步骤:
  1. 如果数组为空,直接返回False
  2. 给数组排序,并将数组内非0的元素组成新数组
  3. 如果新数组的长度等于1,则证明LL抓到了四张王牌,此时肯定是顺子,返回True
  4. 遍历新数组元素,如果相邻数字相减等于0,则证明数组内有相同元素,返回False
  5. 最后将新数组的最大值减去最小值,如果小于等于4,则是顺子,返回True,否则返回False
发表于 2020-07-19 22:00:43 回复(0)
# -*- coding:utf-8 -*-
class Solution:
    def IsContinuous(self, numbers):
        # write code here
        if not numbers: return False
        
        # 如果王有4个以上,那么一定满足要求
        if numbers.count(0) >= 4: return True
        
        # 先把王剔除,并对剩下的牌进行排序
        numbers = sorted([num for num in numbers if num]) 
        
        # 如果有对子,那么肯定不满足要求
        if sorted(set(numbers)) != numbers: return False  
        
        # 如果以上条件都不成立,那么只要牌列中除了王以外最大和最小的数字差小于5即可满足要求
        if numbers[-1] - numbers[0] < 5: return True
        
        # 如果以上条件均不成立
        else: return False


编辑于 2020-06-20 10:35:04 回复(0)
# -*- coding:utf-8 -*-
class Solution:
    def IsContinuous(self, numbers):
        # write code here
        if not numbers:
            return False
        zero = numbers.count(0)
        numbers.sort()
        for i, v in enumerate(numbers[:-1]):
            #因为我们每个都是当前数和下一个数比较,所以只能取到倒数第二个数!
            if v != 0:
                if numbers[i+1] == v:
                #如果五张牌有除了joker以外的牌有两张或两张以上,必然不能成顺子
                    return False
                zero = zero - (numbers[i+1] - v) + 1
                #此zero作为相邻两个数相差大于1的时候,做万能牌用
                #例如:12,13。 13-12 是不用消耗zero的
                if zero < 0:
                    return False
                #说明万能牌不够用,则不可能组成顺子
        return True

编辑于 2020-06-17 21:54:58 回复(1)
# -*- coding:utf-8 -*-

class Solution:
    def IsContinuous(self, numbers):
        n=numbers
        pai=[]
        if len(n)==0:
            return False

        for i in range(len(n)):
            if n[i]!=0:
                pai.append(n[i])
        pai.sort()
        if len(pai)==1:
            return True
        for i in range(len(pai)):
            if pai.count(pai[i])>=2:
                return False
        temp=0
        for i in range(len(pai)-1):
            temp=temp+(pai[i+1]-pai[i]-1)
        if temp<=len(n)-len(pai):
            return True
        else:
            return False

             
        
            
        
            
        # write code here

发表于 2020-05-27 15:58:23 回复(0)
# -*- coding:utf-8 -*-
"""
1. 排序
2. 零的个数
3. 总的间隔区间
4. 零的个数小于间隔区间的个数,则可以补上
5. 注意存在一对的时候不可能有顺子
"""
class Solution:
    def IsContinuous(self, numbers):
        if not numbers:
            return False
        numbers = sorted(numbers)
        num_of_zeros = numbers.count(0)
        num_of_miss = 0
        for i in range(num_of_zeros, len(numbers) - 1):
            if numbers[i] == numbers[i+1]:
                return False
            elif numbers[i] + 1 == numbers[i+1]:
                continue
            else:
                num_of_miss += numbers[i+1] - numbers[i] - 1
        if num_of_zeros >= num_of_miss:
            return True
        else:
            return False


s = Solution()
ans = s.IsContinuous([0,0,3,14,5])
print(ans)

发表于 2020-03-03 18:28:41 回复(0)
class Solution:
    def IsContinuous(self, numbers):
        # write code here
        if not numbers:
            return False
        ns = [n for n in numbers if n != 0]
        return (max(ns) - min(ns) <= 4) and (len(ns) == len(set(ns)))
想法很简单:先把0拿掉,剩下的3个或4个或5个数字只要 1)不重复;2)最大最小差不超过4即可。不用关心具体有几个王。
发表于 2020-02-05 12:55:07 回复(0)
class Solution:
    def IsContinuous(self, numbers):
        # write code here
        if len(numbers)==0:
           return False
        list1=[i for i in numbers]
        list1.sort()
        pre=0
        current=1
        count=0
        count1=0
        if len(numbers)<=2:
           return True
        while(pre<len(numbers)-1):
            if list1[pre]==0:
               count1+=1
            if list1[current]>list1[pre] and list1[pre]!=0:
               count+=list1[current]-list1[pre]-1
            pre+=1
            current+=1
        if list1[pre]==0:
            count1+=1
        if len(numbers)-count1<=1:
            return True
        if count1==count:
            return True
        else:
            return False
本题的方法是通过将排序好的列表,设置两个指针,分别指向第一个非0元素和其下一个元素,然后得到其间到底隔了几个数字。另外就是统计列表中0的个数,最后看0的个数与间隔的数目是否相同。
需要注意的是几个临界调节,总共元素个数小于2的,总共的非零元素小于等于1的,没有元素的情况
发表于 2020-01-07 19:53:36 回复(0)
# -*- coding:utf-8 -*-
# 解题思路:必须满足两个条件才能组成顺子
# 1.除0之外没有数值重复(count + len(st) == 5)
# 2.最大值和最小值的差不能超过5(mx - mn < 5)
class Solution:
    def IsContinuous(self, numbers):
        # write code here
        st = set()
        count = 0
        mx = 0
        mn = float('inf')
        for i in numbers:
            if i == 0:
                count += 1
            else:
                if i > mx:
                    mx = i

                if i < mn:
                    mn = i

                st.add(i)

        if count + len(st) == 5 and mx - mn < 5:
            return True

        return False
    

发表于 2019-12-08 13:18:55 回复(0)