README.md (6275B)
1 <!-- 2 3 @license Apache-2.0 4 5 Copyright (c) 2018 The Stdlib Authors. 6 7 Licensed under the Apache License, Version 2.0 (the "License"); 8 you may not use this file except in compliance with the License. 9 You may obtain a copy of the License at 10 11 http://www.apache.org/licenses/LICENSE-2.0 12 13 Unless required by applicable law or agreed to in writing, software 14 distributed under the License is distributed on an "AS IS" BASIS, 15 WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 16 See the License for the specific language governing permissions and 17 limitations under the License. 18 19 --> 20 21 # doWhileEachRight 22 23 > While a test condition is true, invoke a function for each element in a collection, iterating from right to left. 24 25 <!-- Section to include introductory text. Make sure to keep an empty line after the intro `section` element and another before the `/section` close. --> 26 27 <section class="intro"> 28 29 </section> 30 31 <!-- /.intro --> 32 33 <!-- Package usage documentation. --> 34 35 <section class="usage"> 36 37 ## Usage 38 39 ```javascript 40 var doWhileEachRight = require( '@stdlib/utils/do-while-each-right' ); 41 ``` 42 43 #### doWhileEachRight( collection, fcn, predicate\[, thisArg ] ) 44 45 Invokes a `function` for each element in a `collection`, iterating from right to left, until either a `predicate` function returns `false` or the function has iterated over all `collection` elements. Note that the condition is evaluated **after** executing `fcn`; thus, `fcn` **always** executes at least once. 46 47 ```javascript 48 function predicate( value ) { 49 return ( value === value ); 50 } 51 52 function log( value, index ) { 53 console.log( '%s: %d', index, value ); 54 } 55 56 var arr = [ 1, NaN, 2, 3, 4 ]; 57 58 doWhileEachRight( arr, log, predicate ); 59 /* => 60 4: 4 61 3: 3 62 2: 2 63 1: NaN 64 */ 65 ``` 66 67 Both the `predicate` function and the `function` to apply are provided three arguments: 68 69 - `value`: collection element 70 - `index`: collection index 71 - `collection`: input collection 72 73 If provided an empty `collection`, both `value` and `index` are `undefined`. 74 75 ```javascript 76 function predicate( value ) { 77 return ( value === value ); 78 } 79 80 function log( value, index ) { 81 console.log( '%s: %s', index, value ); 82 } 83 84 var arr = []; 85 86 doWhileEachRight( arr, log, predicate ); 87 /* => 88 undefined: undefined 89 */ 90 ``` 91 92 Basic support for dynamic collections is provided. Note, however, that index incrementation is **not** guaranteed to be monotonically **decreasing**. 93 94 ```javascript 95 var arr = [ 1, 2, 3, 4 ]; 96 var i = 0; 97 98 function predicate( value ) { 99 return ( value === value ); 100 } 101 102 function log1( value, index, collection ) { 103 console.log( '%s: %d', index, value ); 104 i += 1; 105 if ( index === 0 && collection.length < 10 ) { 106 collection.unshift( i+1 ); 107 } 108 } 109 110 doWhileEachRight( arr, log1, predicate ); 111 /* => 112 3: 4 113 2: 3 114 1: 2 115 0: 1 116 0: 5 117 0: 6 118 0: 7 119 0: 8 120 0: 9 121 0: 10 122 */ 123 124 function log2( value, index, collection ) { 125 console.log( '%s: %d', index, value ); 126 collection.pop(); 127 } 128 129 arr = [ 1, 2, 3, 4 ]; 130 131 doWhileEachRight( arr, log2, predicate ); 132 /* => 133 3: 4 134 1: 2 135 */ 136 ``` 137 138 To set the function execution context for the applied function, provide a `thisArg`. 139 140 ```javascript 141 function predicate( value ) { 142 return ( value > 2 ); 143 } 144 145 function sum( value ) { 146 this.sum += value; 147 this.count += 1; 148 } 149 150 var arr = [ 1, NaN, 2, 3, 4 ]; 151 152 var context = { 153 'sum': 0, 154 'count': 0 155 }; 156 157 doWhileEachRight( arr, sum, predicate, context ); 158 159 var mean = context.sum / context.count; 160 // returns 3.0 161 ``` 162 163 </section> 164 165 <!-- /.usage --> 166 167 <!-- Package usage notes. Make sure to keep an empty line after the `section` element and another before the `/section` close. --> 168 169 <section class="notes"> 170 171 ## Notes 172 173 - A `collection` may be either an [`Array`][mdn-array], [`Typed Array`][mdn-typed-array], or an array-like [`Object`][mdn-object] (excluding `strings` and `functions`). 174 175 - The function returns the input `collection`. 176 177 - The function does **not** skip `undefined` elements. 178 179 <!-- eslint-disable no-sparse-arrays --> 180 181 ```javascript 182 function predicate( value ) { 183 return ( value === value ); 184 } 185 186 function log( value, index ) { 187 console.log( '%s: %s', index, value ); 188 } 189 190 var arr = [ 1, , , 4 ]; 191 192 doWhileEachRight( arr, log, predicate ); 193 /* => 194 3: 4 195 2: undefined 196 1: undefined 197 0: 1 198 */ 199 ``` 200 201 - The function provides limited support for dynamic collections (i.e., collections whose `length` changes during execution). 202 203 </section> 204 205 <!-- /.notes --> 206 207 <!-- Package usage examples. --> 208 209 <section class="examples"> 210 211 ## Examples 212 213 <!-- eslint no-undef: "error" --> 214 215 ```javascript 216 var isEven = require( '@stdlib/assert/is-even' ).isPrimitive; 217 var randu = require( '@stdlib/random/base/randu' ); 218 var floor = require( '@stdlib/math/base/special/floor' ); 219 var doWhileEachRight = require( '@stdlib/utils/do-while-each-right' ); 220 221 var arr; 222 var i; 223 var j; 224 225 function predicate( value ) { 226 return ( value === value ); 227 } 228 229 function log( value, index, collection ) { 230 console.log( '%s: %d', index, value ); 231 i += 1; 232 if ( isEven( i ) ) { 233 collection.pop(); 234 } else { 235 collection.unshift( i+1 ); 236 } 237 } 238 239 arr = new Array( 100 ); 240 j = floor( randu()*arr.length ); 241 for ( i = arr.length-1; i >= 0; i-- ) { 242 if ( i === j ) { 243 arr[ i ] = NaN; 244 } else { 245 arr[ i ] = i; 246 } 247 } 248 249 i = 0; 250 doWhileEachRight( arr, log, predicate ); 251 ``` 252 253 </section> 254 255 <!-- /.examples --> 256 257 <!-- Section to include cited references. If references are included, add a horizontal rule *before* the section. Make sure to keep an empty line after the `section` element and another before the `/section` close. --> 258 259 <section class="references"> 260 261 </section> 262 263 <!-- /.references --> 264 265 <!-- Section for all links. Make sure to keep an empty line after the `section` element and another before the `/section` close. --> 266 267 <section class="links"> 268 269 [mdn-array]: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array 270 271 [mdn-typed-array]: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/TypedArray 272 273 [mdn-object]: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Object 274 275 </section> 276 277 <!-- /.links -->