@@ -60,6 +60,24 @@ function advanceStateWithCircuit(args, circuitDefinition, collectStats) {
6060 let controls = args . controls . and ( circuitDefinition . colControls ( col ) . shift ( args . row ) ) ;
6161 let controlTex = KetTextureUtil . control ( args . wireCount , controls ) ;
6262
63+ let statsCallback = statArgs => {
64+ if ( ! collectStats ) {
65+ return ;
66+ }
67+
68+ let { qubitDensities, customGateStats} = _extractStateStatsNeededByCircuitColumn (
69+ statArgs ,
70+ circuitDefinition ,
71+ col ) ;
72+ colQubitDensities . push ( qubitDensities ) ;
73+ for ( let { row, stat} of customGateStats ) {
74+ //noinspection JSUnusedAssignment
75+ customStatsMap . push ( { col, row, out : customStats . length } ) ;
76+ //noinspection JSUnusedAssignment
77+ customStats . push ( stat ) ;
78+ }
79+ } ;
80+
6381 let nextState = _advanceStateWithCircuitDefinitionColumn (
6482 args ,
6583 new CircuitEvalArgs (
@@ -71,28 +89,8 @@ function advanceStateWithCircuit(args, circuitDefinition, collectStats) {
7189 inputState ,
7290 args . customContextFromGates ) ,
7391 circuitDefinition ,
74- col ) ;
75-
76- if ( collectStats ) {
77- let { qubitDensities, customGateStats} = _extractStateStatsNeededByCircuitColumn (
78- nextState , // We want to show stats after post-selection, so we use 'next' instead of 'input'.
79- circuitDefinition ,
80- col ,
81- controls ,
82- controlTex ,
83- args . time ) ;
84- colQubitDensities . push ( qubitDensities ) ;
85- for ( let { row, stat} of customGateStats ) {
86- //noinspection JSUnusedAssignment
87- customStatsMap . push ( {
88- col,
89- row,
90- out : customStats . length
91- } ) ;
92- //noinspection JSUnusedAssignment
93- customStats . push ( stat ) ;
94- }
95- }
92+ col ,
93+ statsCallback ) ;
9694
9795 KetTextureUtil . doneWithTexture ( controlTex , "controlTex in advanceStateWithCircuit" ) ;
9896 return nextState ;
@@ -107,42 +105,36 @@ function advanceStateWithCircuit(args, circuitDefinition, collectStats) {
107105}
108106
109107/**
110- * @param {!WglTexture } state
108+ * @param {!CircuitEvalArgs } args
111109 * @param {!CircuitDefinition } circuitDefinition
112110 * @param {!int } col
113- * @param {!Controls } controls
114- * @param {!WglTexture } controlTex
115- * @param {!number } time
116111 * @private
117112 * @returns {!{qubitDensities:!WglTexture, customGateStats:!Array.<!{row:!int,stat:!WglTexture}>} }
118113 */
119114function _extractStateStatsNeededByCircuitColumn (
120- state ,
115+ args ,
121116 circuitDefinition ,
122- col ,
123- controls ,
124- controlTex ,
125- time ) {
117+ col ) {
126118 // Compute custom stats used by display gates.
127119 let customGateStats = [ ] ;
128120 for ( let row of circuitDefinition . customStatRowsInCol ( col ) ) {
129121 let statArgs = new CircuitEvalArgs (
130- time ,
122+ args . time ,
131123 row ,
132124 circuitDefinition . numWires ,
133- controls ,
134- controlTex ,
135- state ,
125+ args . controls ,
126+ args . controlsTexture ,
127+ args . stateTexture ,
136128 circuitDefinition . colCustomContextFromGates ( col , row ) ) ;
137129 let pipeline = circuitDefinition . columns [ col ] . gates [ row ] . customStatPipelineMaker ( statArgs ) ;
138- let stat = KetTextureUtil . evaluatePipelineWithIntermediateCleanup ( state , pipeline ) ;
130+ let stat = KetTextureUtil . evaluatePipelineWithIntermediateCleanup ( args . stateTexture , pipeline ) ;
139131 customGateStats . push ( { row, stat} ) ;
140132 }
141133
142134 // Compute individual qubit densities, where needed.
143135 let qubitDensities = KetTextureUtil . superpositionToQubitDensities (
144- state ,
145- controls ,
136+ args . stateTexture ,
137+ args . controls ,
146138 circuitDefinition . colHasSingleQubitDisplayMask ( col ) ) ;
147139
148140 return { qubitDensities, customGateStats} ;
@@ -153,14 +145,16 @@ function _extractStateStatsNeededByCircuitColumn(
153145 * @param {!CircuitEvalArgs } args
154146 * @param {!CircuitDefinition } circuitDefinition
155147 * @param {!int } col
148+ * @param {!function(!CircuitEvalArgs) } statsCallback
156149 * @returns {!WglTexture }
157150 * @private
158151 */
159152function _advanceStateWithCircuitDefinitionColumn (
160153 outerContextArgs ,
161154 args ,
162155 circuitDefinition ,
163- col ) {
156+ col ,
157+ statsCallback ) {
164158
165159 let colContext = Util . mergeMaps (
166160 args . customContextFromGates ,
@@ -199,6 +193,8 @@ function _advanceStateWithCircuitDefinitionColumn(
199193 circuitDefinition . textureTransformsInColAt ( col , outerContextArgs . row ) ,
200194 ( v , f ) => f ( colArgsTemplate . withStateTexture ( v ) ) ) ;
201195
196+ statsCallback ( colArgsTemplate . withStateTexture ( almostAlmostNextState ) ) ;
197+
202198 // Apply 'after column' un-setup shaders.
203199 let nextState = KetTextureUtil . aggregateWithReuse (
204200 almostAlmostNextState ,
0 commit comments