Instructions to use ZibinDong/ActionCodec2 with libraries, inference providers, notebooks, and local apps. Follow these links to get started.
- Libraries
- Transformers
How to use ZibinDong/ActionCodec2 with Transformers:
# pip install -U transformers accelerate # Load model directly from transformers import AutoModel model = AutoModel.from_pretrained("ZibinDong/ActionCodec2", trust_remote_code=True, device_map="auto") - Notebooks
- Google Colab
- Kaggle
File size: 9,579 Bytes
895e804 1bfc3f0 895e804 1bfc3f0 895e804 1bfc3f0 895e804 1bfc3f0 895e804 1bfc3f0 895e804 1bfc3f0 895e804 1bfc3f0 895e804 1bfc3f0 895e804 1bfc3f0 895e804 1bfc3f0 895e804 1bfc3f0 895e804 1bfc3f0 895e804 1bfc3f0 895e804 1bfc3f0 895e804 1bfc3f0 895e804 1bfc3f0 895e804 1bfc3f0 895e804 1bfc3f0 895e804 1bfc3f0 | 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 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 246 | """Constrained-generation grammars for the two ActionCodec2 BPE schemes."""
from __future__ import annotations
from collections.abc import Sequence
from numbers import Integral
import numpy as np
from ._validation import active_dimensions
from .bpe import BPESerializer, SetBPESerializer
from .cache import BoundedCache, cached_prefix_state
from .native_backend import native_kernel
def _coverage_metadata(serializer, dims):
cache = getattr(serializer, "_coverage_metadata", None)
if cache is None:
cache = serializer._coverage_metadata = BoundedCache(32)
metadata = cache.get(dims)
if metadata is not None:
return metadata
metadata = {"compiled": None}
if serializer.scheme == "set_bpe":
full = sum(1 << d for d in dims)
metadata["roots"] = np.asarray(
[serializer.spatial.anchor[serializer.root[t]] for t in range(serializer.vocab_size)],
dtype=np.int64,
)
patterns = tuple(
tuple((offset, int(serializer.spatial.support[token])) for offset, token in pattern)
for pattern in serializer.patterns
)
metadata["patterns"] = patterns
metadata["scope"] = np.asarray(
[all(support & ~full == 0 for _, support in pattern) for pattern in patterns],
dtype=bool,
)
else:
phase = np.zeros((len(dims), serializer.vocab_size), dtype=bool)
for index in range(len(dims)):
for token, expansion in enumerate(serializer.vocabulary.token_dims):
phase[index, token] = all(
d == dims[(index + offset) % len(dims)] for offset, d in enumerate(expansion)
)
metadata["phase"] = phase
metadata["lengths"] = np.asarray(serializer.token_cell_counts, dtype=np.int64)
cache[dims] = metadata
return metadata
class _PrefixGrammar:
def _state(self, tokens: Sequence[int]) -> tuple[int, ...] | None:
checked = []
for token in tokens:
if isinstance(token, bool) or not isinstance(token, Integral):
return None
checked.append(int(token))
return cached_prefix_state(
tuple(checked), self._state_cache, self._empty_state, self._advance
)
def _next_token_mask_from_state(self, state: tuple[int, ...]) -> np.ndarray:
cached = self._mask_cache.get(state)
if cached is None:
compiled = self._compiled()
cached = compiled.mask(state) if compiled is not None else self._python_mask(state)
self._mask_cache[state] = cached
return cached.copy()
def next_token_mask(self, tokens: Sequence[int]) -> np.ndarray:
"""Return a boolean vocabulary mask for the next generated token."""
state = self._state(tokens)
if state is None:
raise ValueError("token prefix is not a legal ActionCodec2 stream")
return self._next_token_mask_from_state(state)
def is_complete(self, tokens: Sequence[int]) -> bool:
"""Whether ``tokens`` is exactly one complete trajectory of this horizon."""
state = self._state(tokens)
return state is not None and self._state_is_complete(state)
class ActionCodec2Grammar(_PrefixGrammar):
'Prefix grammar for one exact, fixed-horizon rooted token stream.'
def __init__(
self,
serializer: SetBPESerializer,
*,
horizon: int,
active_dims: Sequence[int] | None = None,
) -> None:
if isinstance(horizon, bool) or not isinstance(horizon, int) or horizon < 1:
raise ValueError("horizon must be a positive integer")
self.horizon = horizon
self.vocab_size = serializer.vocab_size
dims = active_dimensions(active_dims, serializer.spatial.dimension)
self._full = sum(1 << dimension for dimension in dims)
self._metadata = _coverage_metadata(serializer, dims)
self._root_anchor = self._metadata["roots"]
self._patterns = self._metadata["patterns"]
self._in_scope = self._metadata["scope"]
self._mask_cache = BoundedCache(64)
self._state_cache = BoundedCache(256)
self._empty_state = self._initial_state()
self._native = None
self._compiled()
def _compiled(self):
constructor = native_kernel("SetGrammar")
if constructor is None:
return None
if self._native is None:
prototype = self._metadata["compiled"]
if prototype is None:
prototype = self._metadata["compiled"] = constructor(
1, self._full, self._root_anchor.tolist(), self._patterns
)
self._native = prototype.clone(self.horizon)
return self._native
def _advance(self, state: tuple[int, ...], token: int) -> tuple[int, ...] | None:
compiled = self._compiled()
if compiled is not None:
return compiled.advance(state, token)
if not 0 <= token < self.vocab_size or not self._in_scope[token]:
return None
coverage = list(state)
front = next(
(index for index, mask in enumerate(coverage) if mask != self._full), self.horizon
)
if front == self.horizon:
return None
uncovered = self._full & ~coverage[front]
expected_anchor = int(uncovered & -uncovered).bit_length() - 1
if int(self._root_anchor[token]) != expected_anchor:
return None
for offset, support in self._patterns[token]:
step = front + offset
if step >= self.horizon or coverage[step] & support:
return None
coverage[step] |= support
return tuple(coverage)
def _initial_state(self) -> tuple[int, ...]:
return (0,) * self.horizon
def _covered_steps(self, state: tuple[int, ...]) -> int:
return next((i for i, mask in enumerate(state) if mask != self._full), self.horizon)
def _state_is_complete(self, state: tuple[int, ...]) -> bool:
return all(mask == self._full for mask in state)
def _python_mask(self, state: tuple[int, ...]) -> np.ndarray:
if self._state_is_complete(state):
return np.zeros(self.vocab_size, dtype=bool)
front = next(index for index, mask in enumerate(state) if mask != self._full)
uncovered = self._full & ~state[front]
expected_anchor = int(uncovered & -uncovered).bit_length() - 1
mask = (self._root_anchor == expected_anchor) & self._in_scope
for token in np.flatnonzero(mask):
for offset, support in self._patterns[int(token)]:
step = front + offset
if step >= self.horizon or state[step] & support:
mask[token] = False
break
return mask
class ActionCodec2BPEGrammar(_PrefixGrammar):
'Prefix grammar for one exact, fixed-horizon plain-BPE token stream.'
def __init__(
self,
serializer: BPESerializer,
*,
horizon: int,
active_dims: Sequence[int] | None = None,
) -> None:
if isinstance(horizon, bool) or not isinstance(horizon, int) or horizon < 1:
raise ValueError("horizon must be a positive integer")
self.horizon = horizon
self.vocab_size = serializer.vocab_size
dims = active_dimensions(active_dims, serializer.vocabulary.dimension)
self._width = len(dims)
self._cells = horizon * self._width
self._metadata = _coverage_metadata(serializer, dims)
self._token_cells = self._metadata["lengths"]
self._phase = self._metadata["phase"]
self._mask_cache = BoundedCache(64)
self._state_cache = BoundedCache(256)
self._empty_state = self._initial_state()
self._active_dims = dims
self._native = None
self._compiled()
def _compiled(self):
constructor = native_kernel("PlainGrammar")
if constructor is None:
return None
if self._native is None:
prototype = self._metadata["compiled"]
if prototype is None:
prototype = self._metadata["compiled"] = constructor(
1, self._token_cells.tolist(), self._active_dims, self._phase
)
self._native = prototype.clone(self.horizon)
return self._native
def _initial_state(self) -> tuple[int, ...]:
return (0,)
def _covered_steps(self, state: tuple[int, ...]) -> int:
return state[0] // self._width
def _state_is_complete(self, state: tuple[int, ...]) -> bool:
return state[0] == self._cells
def _advance(self, state: tuple[int, ...], token: int) -> tuple[int, ...] | None:
compiled = self._compiled()
if compiled is not None:
return compiled.advance(state, token)
if not 0 <= token < self.vocab_size:
return None
covered = state[0]
length = int(self._token_cells[token])
if covered + length > self._cells:
return None
if not self._phase[covered % self._width, token]:
return None
return (covered + length,)
def _python_mask(self, state: tuple[int, ...]) -> np.ndarray:
covered = state[0]
if covered == self._cells:
return np.zeros(self.vocab_size, dtype=bool)
return self._phase[covered % self._width] & (self._token_cells <= self._cells - covered)
|