需求

对于一个数组array = ["n","v","l","f",...,"y","c","k"];

  • input

    • 当前位置 index
    • 数组的长度 arraySize
    • 基于当前位置,(前/后)滑动窗口的元素数目 windowSize
      • 即 滑动窗口(假定:包含当前元素 array[idx]) 总长:2*windowSize+1
  • output
    • 滑动窗口中的元素下标数组

      • 形如

        • 【中间】idx=3,arraySize=7,windowSzie=2 => [1,2,3,4,5]
        • 【偏前】idx=0,arraySize=7,windowSzie=2 => [5,6,0,1,2]
        • 【偏后】idx=6,arraySize=7,windowSzie=2 => [4,5,6,1,0]

实现思路

  • [1] 循环队列
  • [2] 充分利用模运算的特点:最左边下标 (idx-windowSize)%arraySize 与 最后边下标(idx+windowSize)%arraySize可计算出来

源码 一

利用思路2,节省更多计算资源。

目前存在一种bug,比如 (2,10,3)

class CollectionUtil:
def window(idx,arraySize,windowSize,containsCenterIdx=True): # 实现滑动窗口
"""
获得当前位置的滑动窗口[元素的下标数组]
-----------------------------------
+ idx : 当前位置下标
+ containsCenterIdx : 返回结果中,是否需要包含idex索引本身
+ 获得长为arraySize的列表中,以idex为中心,前后分别长windowSize个元素的的滑动窗口的元素下标数组
+ 默认数组下标最小为0
+ 滑动窗口总长 2*windowSize+1
+ 博文 [url] https://www.cnblogs.com/johnnyzen/p/10905958.html
"""
if idx>=arraySize or idx < 0 or arraySize<1:
raise ValueError("idx '",idx,"' out of arraySize '",arraySize,"' or them is error value!");
if 2*windowSize+1 > arraySize:
raise ValueError("2*windowSize+1 > arraySize! [ windowSize:",windowSize," | arraySize:",arraySize," ]");
window = [];
leftStart = (idx-windowSize)%(arraySize-1); # 1,10,3 -> 7,8,9,0,1,2,3
rightEnd = (idx+windowSize)%(arraySize-1); # 9 0 1 2
isRightWindowContinuous = True if idx+windowSize==rightEnd else False; # 判断右半窗口是否连贯
for i in range(leftStart,leftStart + windowSize): # range(m,n) = [m,n)
window.append(i);
pass;
if containsCenterIdx == True:
window.append(idx);
if isRightWindowContinuous == True:
for i in range(rightEnd-windowSize+1,rightEnd+1): # 2-4+1
window.append(i);
pass;
else : # 不连贯 即 右半窗口,一部分在数组开头,一部分在数组结尾
for i in range(idx+1,arraySize-1+1):
window.append(i);
pass;
for i in range(0,rightEnd):
window.append(i);
pass;
return window;

测试

print(CollectionUtil.window(1,10,3)); # [7, 8, 9, 1, 2, 3, 4]
print(CollectionUtil.window(9,10,3)); # [6, 7, 8, 9, 0, 1, 2]
print(CollectionUtil.window(8,10,4)); # [4, 5, 6, 7, 8, 9, 0, 1, 2]
print(CollectionUtil.window(7,10,4)); # [3, 4, 5, 6, 7, 8, 9, 0, 1]
# print(CollectionUtil.window(3,7,2)); # [1,2,3,4,5]
# print(CollectionUtil.window(0,7,2)); # [5,6,0,1,2]
# print(CollectionUtil.window(6,7,2)); # [4,5,6,0,1]

源码 二

利用循环队列,目前没有bug。

class CircularQueue: # 循环队列
def __init__(self):
self.queue = []*0; # 空列表
self.cursor = 0; def push(self,eles):
if isinstance(eles,Iterable) == True: # 可遍历类型 字符串("dsvvdsv")、列表、元组、字典、集合等
for ele in eles:
self.queue.append(ele);
pass;
else : # 其他,默认为 单元素处理
self.queue.append(eles); def pop(self,index=-1):
return self.queue.pop(index); # index=-1 : 移除最后一个元素
pass; def index(self,obj):
return self.queue.index(obj); def length(self):
return len(self.queue); def next(self,idx=0):
if idx >= len(self.queue)-1:
return {"index":0,"value":self.queue[0]};
else :
return {"index":(idx+1),"value":self.queue[idx+1]}; def prev(self,idx=0):
if idx <=0:
return {"index":(len(self.queue)-1),"value":self.queue[len(self.queue)-1]};
else :
return {"index":(idx-1),"value":self.queue[idx-1]}; def print(self):
print("queue:",self.queue); def window(self,idx,arraySize,windowSize): # 滑动窗口
windowIndexs = [];
for i in range(0,arraySize):
self.push(i); # 初始化
pass;
nextNodeCursor = self.next(idx); # 下一节点游标
prevNodeCursor = self.prev(idx); # 上一节点游标
for i in range(0,windowSize): # 加载前窗口元素
windowIndexs.append(prevNodeCursor["value"]);
prevNodeCursor = self.prev(prevNodeCursor["index"]);
# self.pop(nextNode["index"]);
pass;
windowIndexs.append(idx);
for i in range(0,windowSize): # 加载后窗口元素
windowIndexs.append(nextNodeCursor["value"]);
nextNodeCursor = self.next(nextNodeCursor["index"]);
# self.pop(prevNode["index"]);
pass;
windowIndexs.sort(); # 返回前 排序
return windowIndexs;

测试

print("window:",CircularQueue().window(2,10,3)); # window: [0, 1, 2, 3, 4, 5, 9]

Python之滑动窗口的更多相关文章

  1. python 图片滑动窗口

    METHOD #1: No smooth, just scaling. def pyramid(image, scale=1.5, minSize=(30, 30)): # yield the ori ...

  2. 『Python』图像金字塔、滑动窗口和非极大值抑制实现

    图像金字塔 1.在从cv2.resize中,传入参数时先列后行的 2.使用了python中的生成器,调用时使用for i in pyramid即可 3.scaleFactor是缩放因子,需要保证缩放后 ...

  3. 【剑指Offer】滑动窗口的最大值 解题报告(Python)

    作者: 负雪明烛 id: fuxuemingzhu 个人博客: http://fuxuemingzhu.cn/ 目录 题目描述 解题方法 暴力求解 单调递减队列 日期 题目地址:https://www ...

  4. leetcode 239. 滑动窗口最大值(python)

    1. 题目描述 给定一个数组 nums,有一个大小为 k 的滑动窗口从数组的最左侧移动到数组的最右侧.你只可以看到在滑动窗口内的 k 个数字.滑动窗口每次只向右移动一位. 返回滑动窗口中的最大值. 示 ...

  5. 剑指Offer 64. 滑动窗口的最大值 (其他)

    题目描述 给定一个数组和滑动窗口的大小,找出所有滑动窗口里数值的最大值.例如,如果输入数组{2,3,4,2,6,2,5,1}及滑动窗口的大小3,那么一共存在6个滑动窗口,他们的最大值分别为{4,4,6 ...

  6. LeetCode 第 3 题:无重复字符的最长子串(滑动窗口)

    LeetCode 第 3 题:无重复字符的最长子串 (滑动窗口) 方法:滑动窗口 滑动窗口模板问题:右指针先走,满足了一定条件以后,左指针向前走,直到不满足条件. 特点:左右指针的方向是一致的,并且是 ...

  7. 【Leetcode堆和双端队列】滑动窗口最大值(239)

    题目 给定一个数组 nums,有一个大小为 k 的滑动窗口从数组的最左侧移动到数组的最右侧.你只可以看到在滑动窗口内的 k 个数字.滑动窗口每次只向右移动一位. 返回滑动窗口中的最大值. 示例: 输入 ...

  8. TCP协议可靠性是如何保证之滑动窗口,超时重发,序列号确认应答信号

    原创文章首发于公众号:「码农富哥」,欢迎收藏和关注,如转载请注明出处! TCP 是一种提供可靠性交付的协议. 也就是说,通过 TCP 连接传输的数据,无差错.不丢失.不重复.并且按序到达. 但是在网络 ...

  9. 【LeetCode】480. 滑动窗口中位数 Sliding Window Median(C++)

    作者: 负雪明烛 id: fuxuemingzhu 公众号: 每日算法题 本文关键词:LeetCode,力扣,算法,算法题,滑动窗口,中位数,multiset,刷题群 目录 题目描述 题目大意 解题方 ...

随机推荐

  1. js动画fireworks烟花

    <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/ ...

  2. element ui的表格列设置fixed后做动态表格出现表格错乱

    最近使用element-UI时,使用table做动态表格,当操作列使用fixed时,动态切换表格列设置设置时就会出现错乱,情况如下: 解决方法: 把el-table-column上的key设成一个随机 ...

  3. [CCC 2016] 生命中的圆

    题面 有这么一类题,它让你求一个0/1环经过T轮周围异或过程之后的样子. 周围异或即 a[i][k] = a[i-1][k-1] ^ a[i-1][k+1] ,其中第一维表示轮数,第二维表示位置. 千 ...

  4. 蓝桥 log大侠

    标题:Log大侠 atm参加了速算训练班,经过刻苦修炼,对以2为底的对数算得飞快,人称Log大侠. 一天,Log大侠的好友 drd 有一些整数序列需要变换,Log大侠正好施展法力... 变换的规则是: ...

  5. bbs--点赞

    bbs---点赞 需求分析 页面展示 1 点赞  和   踩灭  按钮展示 1 用户未登录,不处理点赞踩灭,给用户提供登录接口 2 登录 1 第一次点点赞/踩灭 1 点赞成功 数据+1 提示点赞成功 ...

  6. 学数据分析到底要不要掌握Linux-Python基础前传(2)

    使用Python的数据分析师到底要不要掌握Linux? 对于上面的问题,大部分的答案是Python数据分析在windows的环境下跑跑就可以了,没有必要再花时间来学习Linux; 这里jacky有一个 ...

  7. 二、编译安装LAMP之httpd-2.4.4

    回顾 PHP:脚本编程语言,php解释器 Webapp:面向对象的特性 Zend: 第一段:词法分析.句法分析.编译为Opcode: opcode放置于内存中 第二段:执行opcode: opcode ...

  8. Codeforces 1009 F. Dominant Indices(长链剖分/树上启发式合并)

    F. Dominant Indices 题意: 给一颗无向树,根为1.对于每个节点,求其子树中,哪个距离下的节点数量最多.数量相同时,取较小的那个距离. 题目: 这类题一般的做法是树上的启发式合并,复 ...

  9. Go http包执行流程

    Go 语言实现的 Web 服务工作方式与其他形式下的 Web 工作方式并没有什么不同,具体流程如下: -- http包执行流程 Request:来自用户的请求信息,包括 post.get.Cookie ...

  10. smaller programs should improve performance RISC(精简指令集计算机)和CISC(复杂指令集计算机)是当前CPU的两种架构 区别示例

    COMPUTER ORGANIZATION AND ARCHITECTURE DESIGNING FOR PERFORMANCE NINTH EDITION In this section, we l ...