问题描述:

给定一个正整数数组 nums。

找出该数组内乘积小于 k 的连续的子数组的个数。

示例 1:

输入: nums = [10,5,2,6], k = 100
输出: 8
解释: 8个乘积小于100的子数组分别为: [10], [5], [2], [6], [10,5], [5,2], [2,6], [5,2,6]。
需要注意的是 [10,5,2] 并不是乘积小于100的子数组。

说明::

0 < nums.length <= 50000
0 < nums[i] < 1000
0 <= k < 10^6

解题:

class Solution:
def numSubarrayProductLessThanK(self, nums: List[int], k: int) -> int:
#由于nums是由正整数构成,如果k小于等于1,直接返回0
if k<=1:
return 0
#用于存储结果
res = 0
#从左至右依次遍历数组,i相当于左指针
for i in range(len(nums)):
#如果当前值小于k,结果加1
if nums[i]<k :
res+=1
#r为右指针
r=i+1
#记录当前值
cur=nums[i]
#右指针开始遍历
while r<len(nums):
#左指针的值先乘以右指针的值
cur=cur*nums[r]
#如果当前值小于k,说明这个子数组可以
if cur<k:
#值加1
res+=1
#右指针右移一位
r+=1
else:
#否则说明该子数组不行,退出while循环
break
return res

结果:超出时间限制,也过了74个实例,说明思想是正确的。

为什么超出时间限制,是因为在while循环中计算复杂度太过复杂。

改进之后:

class Solution:
def numSubarrayProductLessThanK(self, nums: List[int], k: int) -> int:
if k<=1:
return 0
#l为左指针
res,l=0,0
#用于相乘
tmp = 1
#获取右指针right和当前值val
for right,val in enumerate(nums):
#先乘以一位
tmp = tmp*val
#当前值大于等于k,说明值太大了,最左边的出去,左指针右移一位
while tmp>=k:
tmp=tmp/nums[l]
l+=1
#否则的话,当前符合的子数组个数为right-l+1
res+=right-l+1
return res

结果:核心就是res+=right-l+1

不好理解举个例子就知道了,比如说[10,5,2,6]。k=100

l=0,r=0,tmp=10,此时数组[10],结果有0-0+1=1个,也就是它自己

i=0,r=1,tmp=50,此时数组[10,5],结果有1-0+1=2个,也就是[10,5]和[5]

i=0,r=2,tmp=100,此时数组[10,5,2],此时不符合题意了,tmp变为50,l+1=1,子数组为[5,2],有2-1+1=2个,也就是[5,2]和[2]

i=1,r=3,tmp=60,此时数组为[5,2,6],结果有3-1+1=3个,也就是[2]、[6]、[5,2,6]

所以总共有:1+2+2+3=8个

公式怎么来的呢?

我们可以这么看:正常情况下

[10]:1种,l=0,r=0

[10,5]:3种,重复计算了[10],剩余2种,l=0,r=1,1-0+1=2

[10,5,2]:6种,重复计算了[10]、[5]、[10,5],剩余3种,l=0,r=2,2-0+1=3

[5,2]:3种,重复计算了[5],剩余2种,i=1,r=2,2-1+1=2

[5,2,6]:6种,重复计算了[5]、[2]、[5,2],剩余3种,i=1,r=3,3-1+1=3种

祛除了重复计算的,正好每一轮是r-l+1。

【python-leetcode713-双指针】乘积小于k的子数组的更多相关文章

  1. JZ009乘积小于k的子数组

    title: 乘积小于k的子数组 题目描述 题目链接:乘积小于k的子数组.剑指offer009 解题思路 注意: 一开始的乘积k值就是小的,随着右边窗口移动才会不断增大 怎么样的条件才能更新左窗口:当 ...

  2. [Swift]LeetCode713. 乘积小于K的子数组 | Subarray Product Less Than K

    Your are given an array of positive integers nums. Count and print the number of (contiguous) subarr ...

  3. Java实现 LeetCode 713 乘积小于K的子数组(子集数量+双指针)

    713. 乘积小于K的子数组 给定一个正整数数组 nums. 找出该数组内乘积小于 k 的连续的子数组的个数. 示例 1: 输入: nums = [10,5,2,6], k = 100 输出: 8 解 ...

  4. [LeetCode] Subarray Product Less Than K 子数组乘积小于K

    Your are given an array of positive integers nums. Count and print the number of (contiguous) subarr ...

  5. 560. 和为K的子数组

    Q: A: 1.暴力找所有可能的子数组,n^2个子数组,最长长度n,则n ^3. 2.n^2解法 从1~n-1各起点开始,一直找到结尾,n^2 class Solution { public: int ...

  6. 计蒜客-T1271 完美K倍子数组

    如果一个数组满足长度至少是 22 ,并且其中任意两个不同的元素 A_iAi​ 和 A_j (i \not = j)Aj​(i​=j) 其和 A_i+A_jAi​+Aj​ 都是 KK 的倍数,我们就称 ...

  7. 【LeetCode】560. 和为K的子数组

    560. 和为K的子数组 知识点:数组:前缀和: 题目描述 给定一个整数数组和一个整数 k,你需要找到该数组中和为 k 的连续的子数组的个数. 示例 输入:nums = [1,1,1], k = 2 ...

  8. 动态规划-子数组乘积小于k的总个数 Subarray Product Less Than K

    2018-09-01 23:02:46 问题求解: 问题求解: 最开始的时候,一眼看过去就是一条 dp 嘛,保存每个数字结尾的长度和,最后求和就好,至于长度如何求,本题中需要用滑动窗口来维护. 很好的 ...

  9. LeetCode——560. 和为K的子数组

    给定一个整数数组和一个整数 k,你需要找到该数组中和为 k 的连续的子数组的个数. 示例 1 : 输入:nums = [1,1,1], k = 2 输出: 2 , [1,1] 与 [1,1] 为两种不 ...

随机推荐

  1. 基于 HTML5 + WebGL 的 3D 风力发电场

    前言    风能是一种开发中的洁净能源,它取之不尽.用之不竭.当然,建风力发电场首先应考虑气象条件和社会自然条件.近年来,我国海上和陆上风电发展迅猛.海水.陆地为我们的风力发电提供了很好地质保障.正是 ...

  2. 【Java基础总结】反射

    1. 什么是反射 Class.Method.Field.Constructor,它们是反射对象.它们是类.方法.成员变量.构造器,在内存中的形式. 也就是万物皆对象!类是类型.方法是类型.成员变量是类 ...

  3. Airtest入门篇

    Airtest是啥? 简单理解:基于图像识别的UI自动化测试框架 俗人理解:截图即可完成自动化测试 适用场景:游戏.APP.PC软件,支持Window.Android.IOS Airtest官方文档 ...

  4. 投影方式- Unity3D游戏开发培训

    投影方式- Unity3D游戏开发培训   作者:Jesai 2018-02-12 20:33:13 摘  要 透视投影是3D渲染的基本概念,也是3D程序设计的基础.掌握透视投影的原理对于深入理解其他 ...

  5. Unity3d游戏角色描边

    本文发布于游戏程序员刘宇的个人博客,欢迎转载,请注明来源https://www.cnblogs.com/xiaohutu/p/10834491.html 游戏里经常需要在角色上做描边,这里总结一下平时 ...

  6. idea初使用之自动编译

    原文地址:https://blog.csdn.net/diaomeng11/article/details/73826564/ 因为公司需要,方便使用框架以及代码整合,使用同一开发集成环境idea,因 ...

  7. 使用Async方法 Using Async Methods 精通ASP-NET-MVC-5-弗瑞曼 Listing 4-32.

  8. 数据结构——栈的应用 NOI2.2 括号匹配问题

    栈是一种数据结构,相当于一个容器,将一个又一个变量从顶端压进去,需要使用时,又从顶端拿出来,其具体使用方法,下面是详细讲解: #include<stack>必须使用此头文件 stack&l ...

  9. GCC编译Win图形程序不显示控制台方法

    用VS编译openCV这些有控制台又有图形显示的程序,如果想隐藏控制台,只需要使用一行代码: #pragma comment( linker, "/subsystem:/"wind ...

  10. Qt使用QAxObject快速批量读取Excel内容

    网上各种教程用的方法主要是如下这一句: QAxObject * range = worksheet->querySubObject("Cells(int,int)", 1, ...