FazBrowse GitHub Viewer
|
Trending
|
URL:
|
Home
Tools:
[Download Repo ZIP]
[View Raw Code]
[Original HTTPS Page]
ELF/elf_python/circular_queue.py at master · fairinternal/ELF · GitHub
Uh oh!
There was an error while loading.
Please reload this page
.
This repository was archived by the owner on Sep 28, 2023. It is now read-only.
fairinternal
/
ELF
Public archive
forked from
facebookresearch/ELF
Notifications
You must be signed in to change notification settings
Fork
0
Star
6
Code
Pull requests
0
Actions
Projects
Wiki
Security and quality
0
Insights
Additional navigation options
Code
Pull requests
Actions
Projects
Wiki
Security and quality
Insights
Expand file tree
Breadcrumbs
ELF
/
elf_python
/
circular_queue.py
Copy path
More file actions
More file actions
Latest commit
History
History
History
108 lines (85 loc) · 2.81 KB
Breadcrumbs
ELF
/
elf_python
/
circular_queue.py
Copy path
File metadata and controls
108 lines (85 loc) · 2.81 KB
Raw
Copy raw file
Download raw file
Open symbols panel
Edit and raw actions
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
class
CQueue
:
''' Custom-made circular queue, which is fixed sized.
The motivation here is to have
* O(1) complexity for peeking the center part of the data
In contrast, deque has O(n) complexity
* O(1) complexity to sample from the queue (e.g., sampling replays)
'''
def
__init__
(
self
,
n
):
''' Preallocate n slots for circular queue '''
self
.
n
=
n
self
.
q
=
[
None
]
*
n
# Data always pushed to the tail and popped from the head.
# Head points to the next location to pop.
# Tail points to the next location to push.
# if head == tail, then #size = 0
self
.
head
=
0
self
.
tail
=
0
self
.
sz
=
0
def
_inc
(
self
,
v
):
v
+=
1
if
v
>=
self
.
n
:
v
=
0
return
v
def
_dec
(
self
,
v
):
v
-=
1
if
v
<
0
:
v
=
self
.
n
-
1
return
v
def
_proj
(
self
,
v
):
while
v
>=
self
.
n
:
v
-=
self
.
n
while
v
<
0
:
v
+=
self
.
n
return
v
def
push
(
self
,
m
):
if
self
.
sz
==
self
.
n
:
return
False
self
.
sz
+=
1
self
.
q
[
self
.
tail
]
=
m
self
.
tail
=
self
.
_inc
(
self
.
tail
)
return
True
def
pop
(
self
):
if
self
.
sz
==
0
:
return
self
.
sz
-=
1
m
=
self
.
q
[
self
.
head
]
self
.
head
=
self
.
_inc
(
self
.
head
)
return
m
def
popn
(
self
,
T
):
if
self
.
sz
<
T
:
return
self
.
sz
-=
T
self
.
head
=
self
.
_proj
(
self
.
head
+
T
)
return
True
def
peekn_top
(
self
,
T
):
if
self
.
sz
<
T
:
return
return
list
(
self
.
interval_pop
(
T
))
def
peek_pop
(
self
,
start
=
0
):
if
start
>=
self
.
sz
:
return
i
=
self
.
_proj
(
self
.
head
+
start
)
return
self
.
q
[
i
]
def
interval_pop
(
self
,
region_len
,
start
=
0
):
''' Return an iterator with region_len
The interval is self.head + [start, start+region_len)
'''
if
self
.
sz
<
region_len
-
start
:
raise
IndexError
i
=
self
.
_proj
(
self
.
head
+
start
)
for
j
in
range
(
region_len
):
yield
self
.
q
[
i
]
i
=
self
.
_inc
(
i
)
def
interval_pop_rev
(
self
,
region_len
,
end
=
-
1
):
''' Return a reverse iterator with region_len
The interval is self.head + [end + region_len, end) (in reverse order)
'''
if
self
.
sz
<
end
+
region_len
:
raise
IndexError
i
=
self
.
_proj
(
self
.
head
+
end
+
region_len
)
for
j
in
range
(
region_len
):
yield
self
.
q
[
i
]
i
=
self
.
_dec
(
i
)
def
sample
(
self
,
T
=
1
):
''' Sample from the queue for off-policy methods
We want to sample T consecutive samples.
'''
start
=
random
.
randint
(
0
,
self
.
sz
-
T
)
# Return an iterator
return
self
.
interval_pop
(
T
,
start
=
start
)
def
__len__
(
self
):
return
self
.
sz
Back
|
FazBrowse Home
|
New Git URL