PyrInternalModelB¶
Role: Pure-logit Pyramid internal model for Player B that consumes logit tensors and emits a final communication logit, with optional per-level internal signal tracing.
Location: Q_Sea_Battle.pyr_internal_model_b.PyrInternalModelB
Derived constraints¶
- Define \(n2\) as the gun/state vector width (number of gun/state bits), and define \(m\) as the communication size (
self.Min code). This class enforces \(m = 1\) at construction time. - Define
depthas the number of pyramid levels computed from \(n2\) via_validate_power_of_two(n2); therefore \(n2\) must be a power of two. - For level index \(d \in \{0, \dots, \text{depth}-1\}\), per-level widths are \(k_d = \frac{n2}{2^{d+1}}\); therefore
prev_meas_list[d]andprev_out_list[d]must have trailing dimension \(k_d\) (enforced dynamically viatf.debugging.assert_equalagainst the computed measurement output width at that level).
Constructor¶
| Parameter | Type | Description |
|---|---|---|
game_layout |
Any, constraints: interpreted by _infer_n2_and_m(game_layout) |
Game configuration object used to infer \(n2\) and \(m\). |
sr_mode |
str, constraints: documented as one of {"replay","stochastic"} |
SR mode forwarded to each PRAssistedReplay layer. |
p_rule |
float, constraints: not specified |
Probability parameter forwarded to SR layers (interpretation depends on SR mode). |
beta |
float, constraints: not specified |
Hard-logit inverse-temperature forwarded to SR layers. |
alpha |
float, constraints: not specified |
Gate sharpness forwarded to SR layers. |
seed |
int \| None, constraints: any integer or None |
Optional random seed forwarded to SR layers. |
measure_layers |
Optional[Sequence[tf.keras.layers.Layer]], constraints: if provided, len(measure_layers) == depth |
Optional pre-constructed per-level measurement layers; otherwise constructed as PyrMeasurementLayerB() per level. |
combine_layers |
Optional[Sequence[tf.keras.layers.Layer]], constraints: if provided, len(combine_layers) == depth |
Optional pre-constructed per-level combine layers; otherwise constructed as PyrCombineLayerB() per level. |
name |
Optional[str], constraints: any string or None |
Optional Keras model name passed to tf.keras.Model. |
Preconditions
_infer_n2_and_m(game_layout)must succeed (behavior not specified in this module).- \(m = 1\) (enforced; otherwise
ValueError). - \(n2\) must be a power of two (enforced by
_validate_power_of_two(n2); exact error behavior not specified in this module). - If
measure_layersis provided, it must be a Python sequence with length exactlydepth. - If
combine_layersis provided, it must be a Python sequence with length exactlydepth.
Postconditions
self.n2: intis set from_infer_n2_and_m(game_layout).self.M: intis set from_infer_n2_and_m(game_layout)and is guaranteed to equal1.self.depth: intis set from_validate_power_of_two(self.n2).self.measure_layers: list[tf.keras.layers.Layer]has lengthdepth.self.combine_layers: list[tf.keras.layers.Layer]has lengthdepth.self.sr_layers: list[PRAssistedReplay]has lengthdepthand is populated with onePRAssistedReplay(...)per level using the provided SR hyperparameters.
Errors
ValueError: ifself.M != 1(message indicatescomms_size==1requirement).ValueError: ifmeasure_layersis provided andlen(measure_layers) != depth.ValueError: ifcombine_layersis provided andlen(combine_layers) != depth.
Example
import tensorflow as tf
from Q_Sea_Battle.pyr_internal_model_b import PyrInternalModelB
game_layout = ... # must be compatible with _infer_n2_and_m and yield m=1
model = PyrInternalModelB(game_layout, sr_mode="replay", p_rule=1.0, beta=10.0, alpha=5.0, seed=123)
B = 2
gun_logits = tf.zeros((B, model.n2), dtype=tf.float32)
comm_in_logits = tf.zeros((B, 1), dtype=tf.float32)
prev_meas_list = [tf.zeros((B, model.n2 // (2 ** (d + 1))), dtype=tf.float32) for d in range(model.depth)]
prev_out_list = [tf.zeros((B, model.n2 // (2 ** (d + 1))), dtype=tf.float32) for d in range(model.depth)]
shoot_logit, meas_list, out_list, comms_list, guns_list = model.compute_with_internal(
gun_logits,
comm_in_logits,
prev_meas_list,
prev_out_list,
training=False,
)
Public Methods¶
set_alpha(alpha)¶
Set PR gate sharpness for all PR-assisted SR layers.
Parameters
alpha:float, constraints: not specified, shape: scalar.
Returns
None, constraints: alwaysNone.
Errors
AttributeError: if any SR layer does not implementset_alpha.
set_p_rule(p_rule)¶
Set p_rule for all PR-assisted SR layers.
Parameters
p_rule:float, constraints: not specified, shape: scalar.
Returns
None, constraints: alwaysNone.
Errors
AttributeError: if any SR layer does not implementset_p_rule.
set_beta(beta)¶
Set hard-logit beta for all PR-assisted SR layers.
Parameters
beta:float, constraints: not specified, shape: scalar.
Returns
None, constraints: alwaysNone.
Errors
AttributeError: if any SR layer does not implementset_beta.
set_sr_mode(sr_mode)¶
Set SR mode for all PR-assisted SR layers.
Parameters
sr_mode:str, constraints: not specified by this method (constructor documents{"replay","stochastic"}), shape: scalar string.
Returns
None, constraints: alwaysNone.
Errors
AttributeError: if any SR layer does not implementset_sr_mode.
call(inputs, training=False, **kwargs)¶
Keras/Player-facing forward call delegating to compute_with_internal().
Parameters
inputs:Any, constraints: must belistortuple; accepted shapes: one of the two packings described below.training:bool, constraints: any boolean; shape: scalar.kwargs:dict[str, Any], constraints: unused; accepted for Keras compatibility.
Accepted input packings
- Flat packing:
inputs = [gun_logits, comm_in_logits, *prev_meas_list, *prev_out_list]with total length2 + 2*depth. - Nested packing:
inputs = [gun_logits, comm_in_logits, prev_meas_list, prev_out_list]whereprev_meas_listandprev_out_listarelist/tuple.
Required tensor contracts (enforced in compute_with_internal)
gun_logits:tf.Tensor, dtypefloat32, shape(B, n2).comm_in_logits:tf.Tensor, dtypefloat32, shape(B, 1).prev_meas_list:Sequence[tf.Tensor], constraints: lengthdepth, each dtypefloat32, shape(B, k_d)where \(k_d = \frac{n2}{2^{d+1}}\).prev_out_list:Sequence[tf.Tensor], constraints: lengthdepth, each dtypefloat32, shape(B, k_d)where \(k_d = \frac{n2}{2^{d+1}}\).
Returns
shoot_logit:tf.Tensor, dtypefloat32, shape(B, 1).
Errors
TypeError: ifinputsis not alist/tuple.ValueError: if using flat packing andlen(inputs) != 2 + 2*depth.- Any errors raised by
compute_with_internal(...)for shape/type validation.
compute_with_internal(gun_logits, comm_in_logits, prev_meas_list, prev_out_list, harden_between_levels=False, beta_for_hardening=10.0, *, training=False)¶
Run the pure-logit internal forward pass and return per-level signals.
Parameters
gun_logits:tf.Tensor, dtypefloat32(converted viatf.convert_to_tensor(..., dtype=tf.float32)), shape(B, n2), constraints: rank must be 2; last dimension must equaln2if statically known.comm_in_logits:tf.Tensor, dtypefloat32(converted), shape(B, 1), constraints: rank must be 2; last dimension must equal1if statically known.prev_meas_list:Sequence[tf.Tensor], constraints: must be a Pythonlistortupleof lengthdepth; each element convertible totf.Tensorand cast tofloat32; shape(B, k_d)where \(k_d = \frac{n2}{2^{d+1}}\) (enforced dynamically to match the per-level measurement output width).prev_out_list:Sequence[tf.Tensor], constraints: must be a Pythonlistortupleof lengthdepth; each element convertible totf.Tensorand cast tofloat32; shape `(B, k_d)$ where \(k_d = \frac{n2}{2^{d+1}}\) (enforced dynamically to match the per-level measurement output width).harden_between_levels:bool, constraints: any boolean; shape: scalar; ifTrue, intermediatestate_logits,c_logit, andout_b_logitsare mapped by sign to \(\pm \text{beta\_for\_hardening}\) between levels.beta_for_hardening:float, constraints: not specified; shape: scalar; magnitude used when hardening logits.training:bool, constraints: any boolean; shape: scalar; forwarded to sublayers.
Returns
shoot_logit:tf.Tensor, dtypefloat32, shape(B, 1), constraints: final communication logit.meas_b_logits_list:list[tf.Tensor], dtypefloat32, shape: lengthdepth, each element shape(B, k_d).out_b_logits_list:list[tf.Tensor], dtypefloat32, shape: lengthdepth, each element shape(B, k_d).comms_logits_list:list[tf.Tensor], dtypefloat32, shape: lengthdepth + 1, element 0 is the inputcomm_in_logits(cast/converted), subsequent elements are per-level next comm logits, each shape(B, 1).gun_logits_list:list[tf.Tensor], dtypefloat32, shape: lengthdepth + 1, element 0 is the inputgun_logits(cast/converted), subsequent elements are per-level next gun logits, each shape(B, n2)(exact internal transformation constraints not specified here; output is cast tofloat32).
Errors
ValueError: ifgun_logitsis not rank 2.ValueError: ifgun_logits.shape[-1]is statically known and not equal ton2.ValueError: ifcomm_in_logitsis not rank 2, or if its last dimension is statically known and not equal to1.TypeError: ifprev_meas_listorprev_out_listis not a Pythonlist/tuple.ValueError: iflen(prev_meas_list) != depthorlen(prev_out_list) != depth.tf.errors.InvalidArgumentError(or other TensorFlow assertion errors): may be raised bytf.debugging.assert_equalif per-level trailing dimensions ofprev_meas/prev_outdo not match the measurement output trailing dimension.
Return order
The method returns (shoot_logit, meas_b_logits_list, out_b_logits_list, comms_logits_list, gun_logits_list). A note in code states a legacy implementation returned gun_logits_list and comms_logits_list in the opposite order.
save_weights_to(path)¶
Save model weights to a file, ensuring the model is built first.
Parameters
path:str, constraints: must be a path understood bytf.keras.Model.save_weights; shape: scalar string.
Returns
None, constraints: alwaysNone.
Errors
- Not specified in this module; may raise errors from TensorFlow/Keras I/O and
save_weights.
load_weights_from(path)¶
Load model weights from a file, ensuring the model is built first.
Parameters
path:str, constraints: must be a path understood bytf.keras.Model.load_weights; shape: scalar string.
Returns
None, constraints: alwaysNone.
Errors
- Not specified in this module; may raise errors from TensorFlow/Keras I/O and
load_weights.
Data & State¶
n2:int, constraints: inferred fromgame_layoutby_infer_n2_and_m; represents gun/state width.M:int, constraints: must equal1(enforced); represents communication size \(m\).depth:int, constraints: computed by_validate_power_of_two(n2); number of pyramid levels.measure_layers:list[tf.keras.layers.Layer], constraints: lengthdepth; elements are either provided bymeasure_layersor created asPyrMeasurementLayerB().combine_layers:list[tf.keras.layers.Layer], constraints: lengthdepth; elements are either provided bycombine_layersor created asPyrCombineLayerB().sr_layers:list[PRAssistedReplay], constraints: lengthdepth; one SR layer per level, created in the constructor.- Keras model variables: created lazily;
_ensure_built()runs a dummy forward pass to force variable creation when needed for weight I/O.
Planned (design-spec)¶
- Not specified (no design notes provided beyond in-module docstring).
Deviations¶
- The module-level docstring describes
compute_with_internal()returning five values:shoot_logit, meas_b_list, out_b_list, comms_list, guns_list, but the implementation currently returns exactly five values in that same order; however, the annotated return type in the signature istuple[tf.Tensor, list[tf.Tensor], list[tf.Tensor], list[tf.Tensor], list[tf.Tensor], list[tf.Tensor]](six items), which does not match the actual return statement. - The module-level docstring describes
call()delegating tocompute_with_internal()for player-facing compatibility; the implementation does so, butcall()returns onlyshoot_logitand discards internal lists.
Notes for Contributors¶
- Keep the
compute_with_internal()return type annotation consistent with the actual return tuple length and ordering. compute_with_internal()includes an innerharden_logitshelper defined inside the function; if performance is critical, consider implications of Python closure creation (behavioral changes must be validated)._ensure_built()assumes per-level tensors have trailing dimensionn2 // (2 ** (d + 1)); changes to measurement/combine layer dimensionality contracts must update this dummy-shape logic accordingly.call()supports two input packings; any future changes to input structure must preserve backward compatibility or update adapters accordingly.
Related¶
Q_Sea_Battle.pyr_measurement_layer_b.PyrMeasurementLayerBQ_Sea_Battle.pyr_combine_layer_b.PyrCombineLayerBQ_Sea_Battle.pr_assisted_replay.PRAssistedReplayQ_Sea_Battle.pyr_internal_model_a._infer_n2_and_mQ_Sea_Battle.pyr_internal_model_a._validate_power_of_two
Changelog¶
- Not specified in module.