├── .gitignore ├── .travis.yml ├── LICENSE ├── README.md ├── elm.json ├── src └── Random │ ├── Array.elm │ ├── Char.elm │ ├── Date.elm │ ├── Dict.elm │ ├── Extra.elm │ ├── Float.elm │ ├── Int.elm │ ├── List.elm │ ├── Order.elm │ ├── Set.elm │ └── String.elm └── tests └── Tests └── Random ├── Array.elm ├── Extra.elm └── List.elm /.gitignore: -------------------------------------------------------------------------------- 1 | elm-stuff 2 | -------------------------------------------------------------------------------- /.travis.yml: -------------------------------------------------------------------------------- 1 | language: elm 2 | sudo: false -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | BSD 3-Clause License 2 | 3 | Copyright (c) 2017, Elm Community 4 | All rights reserved. 5 | 6 | Redistribution and use in source and binary forms, with or without 7 | modification, are permitted provided that the following conditions are met: 8 | 9 | * Redistributions of source code must retain the above copyright notice, this 10 | list of conditions and the following disclaimer. 11 | 12 | * Redistributions in binary form must reproduce the above copyright notice, 13 | this list of conditions and the following disclaimer in the documentation 14 | and/or other materials provided with the distribution. 15 | 16 | * Neither the name of the copyright holder nor the names of its 17 | contributors may be used to endorse or promote products derived from 18 | this software without specific prior written permission. 19 | 20 | THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" 21 | AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 22 | IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE 23 | DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE 24 | FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 25 | DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR 26 | SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER 27 | CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, 28 | OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 29 | OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 30 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # elm-community/random-extra 2 | This library includes lots of extra helper functions for the Random module. It makes generating pseudo-random values much easier. 3 | 4 | If you want to add one or find a bug, please [open an issue](https://github.com/elm-community/random-extra/issues/new). If you want to contribute, you can open a PR adding tests. 5 | 6 | ## Changelog 7 | ### 3.2.0 8 | * Add `Random.List.choices` 9 | * Use a uniform shuffle for both `Random.List.shuffle` and `Random.Array.shuffle`. 10 | 11 | ### 3.1.0 12 | * Add `sequence` and `traverse` functions 13 | * Improve the performance of `Random.List.shuffle` and `Random.Array.shuffle`, especially on long lists/arrays. 14 | 15 | ### 3.0.0 16 | * Update for Elm 0.19, including switching to `elm/random`. 17 | * Remove `Color` module. 18 | * Rename `Random.Date.day` to `Random.Date.weekday`. 19 | * Remove many trivial functions in `Random.Date`. 20 | * Add `Random.Extra.bool`. 21 | * Remove `Random.Extra.constant`; it's present in the official library. 22 | * Change the signatures of `Random.Extra.choices` and `Random.Extra.frequency` to require an element and a list, avoid the issue of an empty list. 23 | 24 | 25 | ### 2.0.0 26 | * Update dependencies for Elm 0.18. 27 | * Remove `flatMap` as core's `andThen` is identical. 28 | * Rename `flatMapN` to `andThenN`, for similar reasons. 29 | * Rename `together` to `combine`; see #1. 30 | * Change signature of `Random.Extra.Float.normal`; see #2. 31 | * Add `Random.Extra.List` module; see #4. 32 | -------------------------------------------------------------------------------- /elm.json: -------------------------------------------------------------------------------- 1 | { 2 | "type": "package", 3 | "name": "elm-community/random-extra", 4 | "summary": "Extra functions for the core Random library", 5 | "license": "BSD-3-Clause", 6 | "version": "3.2.0", 7 | "exposed-modules": [ 8 | "Random.Array", 9 | "Random.Char", 10 | "Random.Date", 11 | "Random.Dict", 12 | "Random.Extra", 13 | "Random.Float", 14 | "Random.Int", 15 | "Random.List", 16 | "Random.Order", 17 | "Random.Set", 18 | "Random.String" 19 | ], 20 | "elm-version": "0.19.0 <= v < 0.20.0", 21 | "dependencies": { 22 | "elm/core": "1.0.0 <= v < 2.0.0", 23 | "elm/random": "1.0.0 <= v < 2.0.0", 24 | "elm/time": "1.0.0 <= v < 2.0.0" 25 | }, 26 | "test-dependencies": { 27 | "elm-explorations/test": "1.2.1 <= v < 2.0.0" 28 | } 29 | } 30 | -------------------------------------------------------------------------------- /src/Random/Array.elm: -------------------------------------------------------------------------------- 1 | module Random.Array exposing 2 | ( array, rangeLengthArray 3 | , sample, choose, shuffle 4 | ) 5 | 6 | {-| Extra randomized functions on arrays. 7 | 8 | 9 | # Create an Array 10 | 11 | @docs array, rangeLengthArray 12 | 13 | 14 | # Work with an Array 15 | 16 | @docs sample, choose, shuffle 17 | 18 | -} 19 | 20 | import Array exposing (Array, empty, fromList) 21 | import Random exposing (Generator, andThen, constant, int, list, map) 22 | 23 | 24 | {-| Generate a random array of given size given a random generator 25 | 26 | randomLength5IntArray = 27 | array 5 (int 0 100) 28 | 29 | -} 30 | array : Int -> Generator a -> Generator (Array a) 31 | array arrayLength generator = 32 | map fromList (list arrayLength generator) 33 | 34 | 35 | {-| Generate a random array of random length given a minimum length and 36 | a maximum length. 37 | -} 38 | rangeLengthArray : Int -> Int -> Generator a -> Generator (Array a) 39 | rangeLengthArray minLength maxLength generator = 40 | andThen (\len -> array len generator) (int minLength maxLength) 41 | 42 | 43 | {-| Sample with replacement: produce a randomly selected element of the 44 | array, or `Nothing` for an empty array. Takes O(1) time. 45 | -} 46 | sample : Array a -> Generator (Maybe a) 47 | sample arr = 48 | let 49 | gen = 50 | Random.int 0 (Array.length arr - 1) 51 | in 52 | Random.map (\index -> Array.get index arr) gen 53 | 54 | 55 | {-| Sample without replacement: produce a randomly selected element of the 56 | array, and the array with that element omitted (shifting all later elements 57 | down). If the array is empty, the selected element will be `Nothing`. 58 | -} 59 | choose : Array a -> Generator ( Maybe a, Array a ) 60 | choose arr = 61 | if Array.isEmpty arr then 62 | constant ( Nothing, arr ) 63 | 64 | else 65 | let 66 | lastIndex = 67 | Array.length arr - 1 68 | 69 | front i = 70 | Array.slice 0 i arr 71 | 72 | back i = 73 | if 74 | i == lastIndex 75 | -- workaround for #1 76 | then 77 | Array.empty 78 | 79 | else 80 | Array.slice (i + 1) (lastIndex + 1) arr 81 | 82 | gen = 83 | Random.int 0 lastIndex 84 | in 85 | Random.map 86 | (\index -> 87 | ( Array.get index arr, Array.append (front index) (back index) ) 88 | ) 89 | gen 90 | 91 | 92 | anyInt : Generator Int 93 | anyInt = 94 | Random.int Random.minInt Random.maxInt 95 | 96 | 97 | {-| Shuffle the list. Takes O(_n_ log _n_) time and no extra space. 98 | -} 99 | shuffle : Array a -> Generator (Array a) 100 | shuffle arr = 101 | Random.map 102 | (\independentSeed -> 103 | arr 104 | |> Array.foldl 105 | (\item ( acc, seed ) -> 106 | let 107 | ( tag, nextSeed ) = 108 | Random.step anyInt seed 109 | in 110 | ( ( item, tag ) :: acc, nextSeed ) 111 | ) 112 | ( [], independentSeed ) 113 | |> Tuple.first 114 | |> List.sortBy Tuple.second 115 | |> List.foldl (Array.push << Tuple.first) Array.empty 116 | ) 117 | Random.independentSeed 118 | -------------------------------------------------------------------------------- /src/Random/Char.elm: -------------------------------------------------------------------------------- 1 | module Random.Char exposing 2 | ( char, lowerCaseLatin, upperCaseLatin, latin, english, ascii, unicode 3 | , basicLatin, latin1Supplement, latinExtendedA, latinExtendedB, ipaExtensions, spacingModifier, combiningDiacriticalMarks, greekAndCoptic, cyrillic, cyrillicSupplement, armenian, hebrew, arabic, syriac, arabicSupplement, thaana, nko, samaritan, mandaic, arabicExtendedA, devanagari, bengali, gurmukhi, gujarati, oriya, tamil, telugu, kannada, malayalam, sinhala, thai, lao, tibetan, myanmar, georgian, hangulJamo, ethiopic, ethiopicSupplement, cherokee, unifiedCanadianAboriginalSyllabic, ogham, runic, tagalog, hanunoo, buhid, tagbanwa, khmer, mongolian, unifiedCanadianAboriginalSyllabicExtended, limbu, taiLe, newTaiLue, khmerSymbol, buginese, taiTham, balinese, sundanese, batak, lepcha, olChiki, sundaneseSupplement, vedicExtensions, phoneticExtensions, phoneticExtensionsSupplement, combiningDiacriticalMarksSupplement, latinExtendedAdditional, greekExtended, generalPunctuation, superscriptOrSubscript, currencySymbol, combiningDiacriticalMarksForSymbols, letterlikeSymbol, numberForm, arrow, mathematicalOperator, miscellaneousTechnical, controlPicture, opticalCharacterRecognition, enclosedAlphanumeric, boxDrawing, blockElement, geometricShape, miscellaneousSymbol, dingbat, miscellaneousMathematicalSymbolA, supplementalArrowA, braillePattern, supplementalArrowB, miscellaneousMathematicalSymbolB, supplementalMathematicalOperator, miscellaneousSymbolOrArrow, glagolitic, latinExtendedC, coptic, georgianSupplement, tifinagh, ethiopicExtended, cyrillicExtendedA, supplementalPunctuation, cjkRadicalSupplement, kangxiRadical, ideographicDescription, cjkSymbolOrPunctuation, hiragana, katakana, bopomofo, hangulCompatibilityJamo, kanbun, bopomofoExtended, cjkStroke, katakanaPhoneticExtension, enclosedCJKLetterOrMonth, cjkCompatibility, cjkUnifiedIdeographExtensionA, yijingHexagramSymbol, cjkUnifiedIdeograph, yiSyllable, yiRadical, lisu, vai, cyrillicExtendedB, bamum, modifierToneLetter, latinExtendedD, sylotiNagri, commonIndicNumberForm, phagsPa, saurashtra, devanagariExtended, kayahLi, rejang, hangulJamoExtendedA, javanese, cham, myanmarExtendedA, taiViet, meeteiMayekExtension, ethiopicExtendedA, meeteiMayek, hangulSyllable, hangulJamoExtendedB, highSurrogate, highPrivateUseSurrogate, lowSurrogate, privateUseArea, cjkCompatibilityIdeograph, alphabeticPresentationForm, arabicPresentationFormA, variationSelector, verticalForm, combiningHalfMark, cjkCompatibilityForm, smallFormVariant, arabicPresentationFormB, halfwidthOrFullwidthForm, special, linearBSyllable, linearBIdeogram, aegeanNumber, ancientGreekNumber, ancientSymbol, phaistosDisc, lycian, carian, oldItalic, gothic, ugaritic, oldPersian, deseret, shavian, osmanya, cypriotSyllable, imperialAramaic, phoenician, lydian, meroiticHieroglyph, meroiticCursive, kharoshthi, oldSouthArabian, avestan, inscriptionalParthian, inscriptionalPahlavi, oldTurkic, rumiNumericalSymbol, brahmi, kaithi, soraSompeng, chakma, sharada, takri, cuneiform, cuneiformNumberOrPunctuation, egyptianHieroglyph, bamumSupplement, miao, kanaSupplement, byzantineMusicalSymbol, musicalSymbol, ancientGreekMusicalNotationSymbol, taiXuanJingSymbol, countingRodNumeral, mathematicalAlphanumericSymbol, arabicMathematicalAlphabeticSymbol, mahjongTile, dominoTile, playingCard, enclosedAlphanumericSupplement, enclosedIdeographicSupplement, miscellaneousSymbolOrPictograph, emoticon, transportOrMapSymbol, alchemicalSymbol, cjkUnifiedIdeographExtensionB, cjkUnifiedIdeographExtensionC, cjkUnifiedIdeographExtensionD, cjkCompatibilityIdeographSupplement, tag, variationSelectorSupplement, supplementaryPrivateUseAreaA, supplementaryPrivateUseAreaB 4 | ) 5 | 6 | {-| Extra randomized functions on characters. 7 | 8 | 9 | # Basic Generators 10 | 11 | @docs char, lowerCaseLatin, upperCaseLatin, latin, english, ascii, unicode 12 | 13 | 14 | # Unicode Generators (UTF-8) 15 | 16 | @docs basicLatin, latin1Supplement, latinExtendedA, latinExtendedB, ipaExtensions, spacingModifier, combiningDiacriticalMarks, greekAndCoptic, cyrillic, cyrillicSupplement, armenian, hebrew, arabic, syriac, arabicSupplement, thaana, nko, samaritan, mandaic, arabicExtendedA, devanagari, bengali, gurmukhi, gujarati, oriya, tamil, telugu, kannada, malayalam, sinhala, thai, lao, tibetan, myanmar, georgian, hangulJamo, ethiopic, ethiopicSupplement, cherokee, unifiedCanadianAboriginalSyllabic, ogham, runic, tagalog, hanunoo, buhid, tagbanwa, khmer, mongolian, unifiedCanadianAboriginalSyllabicExtended, limbu, taiLe, newTaiLue, khmerSymbol, buginese, taiTham, balinese, sundanese, batak, lepcha, olChiki, sundaneseSupplement, vedicExtensions, phoneticExtensions, phoneticExtensionsSupplement, combiningDiacriticalMarksSupplement, latinExtendedAdditional, greekExtended, generalPunctuation, superscriptOrSubscript, currencySymbol, combiningDiacriticalMarksForSymbols, letterlikeSymbol, numberForm, arrow, mathematicalOperator, miscellaneousTechnical, controlPicture, opticalCharacterRecognition, enclosedAlphanumeric, boxDrawing, blockElement, geometricShape, miscellaneousSymbol, dingbat, miscellaneousMathematicalSymbolA, supplementalArrowA, braillePattern, supplementalArrowB, miscellaneousMathematicalSymbolB, supplementalMathematicalOperator, miscellaneousSymbolOrArrow, glagolitic, latinExtendedC, coptic, georgianSupplement, tifinagh, ethiopicExtended, cyrillicExtendedA, supplementalPunctuation, cjkRadicalSupplement, kangxiRadical, ideographicDescription, cjkSymbolOrPunctuation, hiragana, katakana, bopomofo, hangulCompatibilityJamo, kanbun, bopomofoExtended, cjkStroke, katakanaPhoneticExtension, enclosedCJKLetterOrMonth, cjkCompatibility, cjkUnifiedIdeographExtensionA, yijingHexagramSymbol, cjkUnifiedIdeograph, yiSyllable, yiRadical, lisu, vai, cyrillicExtendedB, bamum, modifierToneLetter, latinExtendedD, sylotiNagri, commonIndicNumberForm, phagsPa, saurashtra, devanagariExtended, kayahLi, rejang, hangulJamoExtendedA, javanese, cham, myanmarExtendedA, taiViet, meeteiMayekExtension, ethiopicExtendedA, meeteiMayek, hangulSyllable, hangulJamoExtendedB, highSurrogate, highPrivateUseSurrogate, lowSurrogate, privateUseArea, cjkCompatibilityIdeograph, alphabeticPresentationForm, arabicPresentationFormA, variationSelector, verticalForm, combiningHalfMark, cjkCompatibilityForm, smallFormVariant, arabicPresentationFormB, halfwidthOrFullwidthForm, special, linearBSyllable, linearBIdeogram, aegeanNumber, ancientGreekNumber, ancientSymbol, phaistosDisc, lycian, carian, oldItalic, gothic, ugaritic, oldPersian, deseret, shavian, osmanya, cypriotSyllable, imperialAramaic, phoenician, lydian, meroiticHieroglyph, meroiticCursive, kharoshthi, oldSouthArabian, avestan, inscriptionalParthian, inscriptionalPahlavi, oldTurkic, rumiNumericalSymbol, brahmi, kaithi, soraSompeng, chakma, sharada, takri, cuneiform, cuneiformNumberOrPunctuation, egyptianHieroglyph, bamumSupplement, miao, kanaSupplement, byzantineMusicalSymbol, musicalSymbol, ancientGreekMusicalNotationSymbol, taiXuanJingSymbol, countingRodNumeral, mathematicalAlphanumericSymbol, arabicMathematicalAlphabeticSymbol, mahjongTile, dominoTile, playingCard, enclosedAlphanumericSupplement, enclosedIdeographicSupplement, miscellaneousSymbolOrPictograph, emoticon, transportOrMapSymbol, alchemicalSymbol, cjkUnifiedIdeographExtensionB, cjkUnifiedIdeographExtensionC, cjkUnifiedIdeographExtensionD, cjkCompatibilityIdeographSupplement, tag, variationSelectorSupplement, supplementaryPrivateUseAreaA, supplementaryPrivateUseAreaB 17 | 18 | -} 19 | 20 | import Char exposing (fromCode) 21 | import Random exposing (Generator, int, map) 22 | import Random.Extra exposing (choices) 23 | 24 | 25 | {-| Generate a random character within a certain keyCode range 26 | 27 | lowerCaseLetter = 28 | char 65 90 29 | 30 | -} 31 | char : Int -> Int -> Generator Char 32 | char start end = 33 | map fromCode (int start end) 34 | 35 | 36 | {-| Generate a random upper-case Latin Letter 37 | -} 38 | upperCaseLatin : Generator Char 39 | upperCaseLatin = 40 | char 65 90 41 | 42 | 43 | {-| Generate a random lower-case Latin Letter 44 | -} 45 | lowerCaseLatin : Generator Char 46 | lowerCaseLatin = 47 | char 97 122 48 | 49 | 50 | {-| Generate a random Latin Letter 51 | -} 52 | latin : Generator Char 53 | latin = 54 | choices lowerCaseLatin [ upperCaseLatin ] 55 | 56 | 57 | {-| Generate a random English Letter (alias for `latin`) 58 | -} 59 | english : Generator Char 60 | english = 61 | latin 62 | 63 | 64 | {-| Generate a random ASCII Character 65 | -} 66 | ascii : Generator Char 67 | ascii = 68 | char 0 127 69 | 70 | 71 | {-| Generate a random Character in the valid unicode range. 72 | Note: This can produce garbage values as unicode doesn't use all valid values. 73 | To test for specific languages and character sets, use the appropriate one 74 | from the list. 75 | -} 76 | unicode : Generator Char 77 | unicode = 78 | char 0 1114111 79 | 80 | 81 | {-| UTF-8 82 | -} 83 | basicLatin : Generator Char 84 | basicLatin = 85 | char 0 127 86 | 87 | 88 | {-| -} 89 | latin1Supplement : Generator Char 90 | latin1Supplement = 91 | char 128 255 92 | 93 | 94 | {-| -} 95 | latinExtendedA : Generator Char 96 | latinExtendedA = 97 | char 256 383 98 | 99 | 100 | {-| -} 101 | latinExtendedB : Generator Char 102 | latinExtendedB = 103 | char 384 591 104 | 105 | 106 | {-| -} 107 | ipaExtensions : Generator Char 108 | ipaExtensions = 109 | char 592 687 110 | 111 | 112 | {-| -} 113 | spacingModifier : Generator Char 114 | spacingModifier = 115 | char 688 767 116 | 117 | 118 | {-| -} 119 | combiningDiacriticalMarks : Generator Char 120 | combiningDiacriticalMarks = 121 | char 768 879 122 | 123 | 124 | {-| -} 125 | greekAndCoptic : Generator Char 126 | greekAndCoptic = 127 | char 880 1023 128 | 129 | 130 | {-| -} 131 | cyrillic : Generator Char 132 | cyrillic = 133 | char 1024 1279 134 | 135 | 136 | {-| -} 137 | cyrillicSupplement : Generator Char 138 | cyrillicSupplement = 139 | char 1280 1327 140 | 141 | 142 | {-| -} 143 | armenian : Generator Char 144 | armenian = 145 | char 1328 1423 146 | 147 | 148 | {-| -} 149 | hebrew : Generator Char 150 | hebrew = 151 | char 1424 1535 152 | 153 | 154 | {-| -} 155 | arabic : Generator Char 156 | arabic = 157 | char 1536 1791 158 | 159 | 160 | {-| -} 161 | syriac : Generator Char 162 | syriac = 163 | char 1792 1871 164 | 165 | 166 | {-| -} 167 | arabicSupplement : Generator Char 168 | arabicSupplement = 169 | char 1872 1919 170 | 171 | 172 | {-| -} 173 | thaana : Generator Char 174 | thaana = 175 | char 1920 1983 176 | 177 | 178 | {-| -} 179 | nko : Generator Char 180 | nko = 181 | char 1984 2047 182 | 183 | 184 | {-| -} 185 | samaritan : Generator Char 186 | samaritan = 187 | char 2048 2111 188 | 189 | 190 | {-| -} 191 | mandaic : Generator Char 192 | mandaic = 193 | char 2112 2143 194 | 195 | 196 | {-| -} 197 | arabicExtendedA : Generator Char 198 | arabicExtendedA = 199 | char 2208 2303 200 | 201 | 202 | {-| -} 203 | devanagari : Generator Char 204 | devanagari = 205 | char 2304 2431 206 | 207 | 208 | {-| -} 209 | bengali : Generator Char 210 | bengali = 211 | char 2432 2559 212 | 213 | 214 | {-| -} 215 | gurmukhi : Generator Char 216 | gurmukhi = 217 | char 2560 2687 218 | 219 | 220 | {-| -} 221 | gujarati : Generator Char 222 | gujarati = 223 | char 2688 2815 224 | 225 | 226 | {-| -} 227 | oriya : Generator Char 228 | oriya = 229 | char 2816 2943 230 | 231 | 232 | {-| -} 233 | tamil : Generator Char 234 | tamil = 235 | char 2944 3071 236 | 237 | 238 | {-| -} 239 | telugu : Generator Char 240 | telugu = 241 | char 3072 3199 242 | 243 | 244 | {-| -} 245 | kannada : Generator Char 246 | kannada = 247 | char 3200 3327 248 | 249 | 250 | {-| -} 251 | malayalam : Generator Char 252 | malayalam = 253 | char 3328 3455 254 | 255 | 256 | {-| -} 257 | sinhala : Generator Char 258 | sinhala = 259 | char 3456 3583 260 | 261 | 262 | {-| -} 263 | thai : Generator Char 264 | thai = 265 | char 3584 3711 266 | 267 | 268 | {-| -} 269 | lao : Generator Char 270 | lao = 271 | char 3712 3839 272 | 273 | 274 | {-| -} 275 | tibetan : Generator Char 276 | tibetan = 277 | char 3840 4095 278 | 279 | 280 | {-| -} 281 | myanmar : Generator Char 282 | myanmar = 283 | char 4096 4255 284 | 285 | 286 | {-| -} 287 | georgian : Generator Char 288 | georgian = 289 | char 4256 4351 290 | 291 | 292 | {-| -} 293 | hangulJamo : Generator Char 294 | hangulJamo = 295 | char 4352 4607 296 | 297 | 298 | {-| -} 299 | ethiopic : Generator Char 300 | ethiopic = 301 | char 4608 4991 302 | 303 | 304 | {-| -} 305 | ethiopicSupplement : Generator Char 306 | ethiopicSupplement = 307 | char 4992 5023 308 | 309 | 310 | {-| -} 311 | cherokee : Generator Char 312 | cherokee = 313 | char 5024 5119 314 | 315 | 316 | {-| -} 317 | unifiedCanadianAboriginalSyllabic : Generator Char 318 | unifiedCanadianAboriginalSyllabic = 319 | char 5120 5759 320 | 321 | 322 | {-| -} 323 | ogham : Generator Char 324 | ogham = 325 | char 5760 5791 326 | 327 | 328 | {-| -} 329 | runic : Generator Char 330 | runic = 331 | char 5792 5887 332 | 333 | 334 | {-| -} 335 | tagalog : Generator Char 336 | tagalog = 337 | char 5888 5919 338 | 339 | 340 | {-| -} 341 | hanunoo : Generator Char 342 | hanunoo = 343 | char 5920 5951 344 | 345 | 346 | {-| -} 347 | buhid : Generator Char 348 | buhid = 349 | char 5952 5983 350 | 351 | 352 | {-| -} 353 | tagbanwa : Generator Char 354 | tagbanwa = 355 | char 5984 6015 356 | 357 | 358 | {-| -} 359 | khmer : Generator Char 360 | khmer = 361 | char 6016 6143 362 | 363 | 364 | {-| -} 365 | mongolian : Generator Char 366 | mongolian = 367 | char 6144 6319 368 | 369 | 370 | {-| -} 371 | unifiedCanadianAboriginalSyllabicExtended : Generator Char 372 | unifiedCanadianAboriginalSyllabicExtended = 373 | char 6320 6399 374 | 375 | 376 | {-| -} 377 | limbu : Generator Char 378 | limbu = 379 | char 6400 6479 380 | 381 | 382 | {-| -} 383 | taiLe : Generator Char 384 | taiLe = 385 | char 6480 6527 386 | 387 | 388 | {-| -} 389 | newTaiLue : Generator Char 390 | newTaiLue = 391 | char 6528 6623 392 | 393 | 394 | {-| -} 395 | khmerSymbol : Generator Char 396 | khmerSymbol = 397 | char 6624 6655 398 | 399 | 400 | {-| -} 401 | buginese : Generator Char 402 | buginese = 403 | char 6656 6687 404 | 405 | 406 | {-| -} 407 | taiTham : Generator Char 408 | taiTham = 409 | char 6688 6831 410 | 411 | 412 | {-| -} 413 | balinese : Generator Char 414 | balinese = 415 | char 6912 7039 416 | 417 | 418 | {-| -} 419 | sundanese : Generator Char 420 | sundanese = 421 | char 7040 7103 422 | 423 | 424 | {-| -} 425 | batak : Generator Char 426 | batak = 427 | char 7104 7167 428 | 429 | 430 | {-| -} 431 | lepcha : Generator Char 432 | lepcha = 433 | char 7168 7247 434 | 435 | 436 | {-| -} 437 | olChiki : Generator Char 438 | olChiki = 439 | char 7248 7295 440 | 441 | 442 | {-| -} 443 | sundaneseSupplement : Generator Char 444 | sundaneseSupplement = 445 | char 7360 7375 446 | 447 | 448 | {-| -} 449 | vedicExtensions : Generator Char 450 | vedicExtensions = 451 | char 7376 7423 452 | 453 | 454 | {-| -} 455 | phoneticExtensions : Generator Char 456 | phoneticExtensions = 457 | char 7424 7551 458 | 459 | 460 | {-| -} 461 | phoneticExtensionsSupplement : Generator Char 462 | phoneticExtensionsSupplement = 463 | char 7552 7615 464 | 465 | 466 | {-| -} 467 | combiningDiacriticalMarksSupplement : Generator Char 468 | combiningDiacriticalMarksSupplement = 469 | char 7616 7679 470 | 471 | 472 | {-| -} 473 | latinExtendedAdditional : Generator Char 474 | latinExtendedAdditional = 475 | char 7680 7935 476 | 477 | 478 | {-| -} 479 | greekExtended : Generator Char 480 | greekExtended = 481 | char 7936 8191 482 | 483 | 484 | {-| -} 485 | generalPunctuation : Generator Char 486 | generalPunctuation = 487 | char 8192 8303 488 | 489 | 490 | {-| -} 491 | superscriptOrSubscript : Generator Char 492 | superscriptOrSubscript = 493 | char 8304 8351 494 | 495 | 496 | {-| -} 497 | currencySymbol : Generator Char 498 | currencySymbol = 499 | char 8352 8399 500 | 501 | 502 | {-| -} 503 | combiningDiacriticalMarksForSymbols : Generator Char 504 | combiningDiacriticalMarksForSymbols = 505 | char 8400 8447 506 | 507 | 508 | {-| -} 509 | letterlikeSymbol : Generator Char 510 | letterlikeSymbol = 511 | char 8448 8527 512 | 513 | 514 | {-| -} 515 | numberForm : Generator Char 516 | numberForm = 517 | char 8528 8591 518 | 519 | 520 | {-| -} 521 | arrow : Generator Char 522 | arrow = 523 | char 8592 8703 524 | 525 | 526 | {-| -} 527 | mathematicalOperator : Generator Char 528 | mathematicalOperator = 529 | char 8704 8959 530 | 531 | 532 | {-| -} 533 | miscellaneousTechnical : Generator Char 534 | miscellaneousTechnical = 535 | char 8960 9215 536 | 537 | 538 | {-| -} 539 | controlPicture : Generator Char 540 | controlPicture = 541 | char 9216 9279 542 | 543 | 544 | {-| -} 545 | opticalCharacterRecognition : Generator Char 546 | opticalCharacterRecognition = 547 | char 9280 9311 548 | 549 | 550 | {-| -} 551 | enclosedAlphanumeric : Generator Char 552 | enclosedAlphanumeric = 553 | char 9312 9471 554 | 555 | 556 | {-| -} 557 | boxDrawing : Generator Char 558 | boxDrawing = 559 | char 9472 9599 560 | 561 | 562 | {-| -} 563 | blockElement : Generator Char 564 | blockElement = 565 | char 9600 9631 566 | 567 | 568 | {-| -} 569 | geometricShape : Generator Char 570 | geometricShape = 571 | char 9632 9727 572 | 573 | 574 | {-| -} 575 | miscellaneousSymbol : Generator Char 576 | miscellaneousSymbol = 577 | char 9728 9983 578 | 579 | 580 | {-| -} 581 | dingbat : Generator Char 582 | dingbat = 583 | char 9984 10175 584 | 585 | 586 | {-| -} 587 | miscellaneousMathematicalSymbolA : Generator Char 588 | miscellaneousMathematicalSymbolA = 589 | char 10176 10223 590 | 591 | 592 | {-| -} 593 | supplementalArrowA : Generator Char 594 | supplementalArrowA = 595 | char 10224 10239 596 | 597 | 598 | {-| -} 599 | braillePattern : Generator Char 600 | braillePattern = 601 | char 10240 10495 602 | 603 | 604 | {-| -} 605 | supplementalArrowB : Generator Char 606 | supplementalArrowB = 607 | char 10496 10623 608 | 609 | 610 | {-| -} 611 | miscellaneousMathematicalSymbolB : Generator Char 612 | miscellaneousMathematicalSymbolB = 613 | char 10624 10751 614 | 615 | 616 | {-| -} 617 | supplementalMathematicalOperator : Generator Char 618 | supplementalMathematicalOperator = 619 | char 10752 11007 620 | 621 | 622 | {-| -} 623 | miscellaneousSymbolOrArrow : Generator Char 624 | miscellaneousSymbolOrArrow = 625 | char 11008 11263 626 | 627 | 628 | {-| -} 629 | glagolitic : Generator Char 630 | glagolitic = 631 | char 11264 11359 632 | 633 | 634 | {-| -} 635 | latinExtendedC : Generator Char 636 | latinExtendedC = 637 | char 11360 11391 638 | 639 | 640 | {-| -} 641 | coptic : Generator Char 642 | coptic = 643 | char 11392 11519 644 | 645 | 646 | {-| -} 647 | georgianSupplement : Generator Char 648 | georgianSupplement = 649 | char 11520 11567 650 | 651 | 652 | {-| -} 653 | tifinagh : Generator Char 654 | tifinagh = 655 | char 11568 11647 656 | 657 | 658 | {-| -} 659 | ethiopicExtended : Generator Char 660 | ethiopicExtended = 661 | char 11648 11743 662 | 663 | 664 | {-| -} 665 | cyrillicExtendedA : Generator Char 666 | cyrillicExtendedA = 667 | char 11744 11775 668 | 669 | 670 | {-| -} 671 | supplementalPunctuation : Generator Char 672 | supplementalPunctuation = 673 | char 11776 11903 674 | 675 | 676 | {-| -} 677 | cjkRadicalSupplement : Generator Char 678 | cjkRadicalSupplement = 679 | char 11904 12031 680 | 681 | 682 | {-| -} 683 | kangxiRadical : Generator Char 684 | kangxiRadical = 685 | char 12032 12255 686 | 687 | 688 | {-| -} 689 | ideographicDescription : Generator Char 690 | ideographicDescription = 691 | char 12272 12287 692 | 693 | 694 | {-| -} 695 | cjkSymbolOrPunctuation : Generator Char 696 | cjkSymbolOrPunctuation = 697 | char 12288 12351 698 | 699 | 700 | {-| -} 701 | hiragana : Generator Char 702 | hiragana = 703 | char 12352 12447 704 | 705 | 706 | {-| -} 707 | katakana : Generator Char 708 | katakana = 709 | char 12448 12543 710 | 711 | 712 | {-| -} 713 | bopomofo : Generator Char 714 | bopomofo = 715 | char 12544 12591 716 | 717 | 718 | {-| -} 719 | hangulCompatibilityJamo : Generator Char 720 | hangulCompatibilityJamo = 721 | char 12592 12687 722 | 723 | 724 | {-| -} 725 | kanbun : Generator Char 726 | kanbun = 727 | char 12688 12703 728 | 729 | 730 | {-| -} 731 | bopomofoExtended : Generator Char 732 | bopomofoExtended = 733 | char 12704 12735 734 | 735 | 736 | {-| -} 737 | cjkStroke : Generator Char 738 | cjkStroke = 739 | char 12736 12783 740 | 741 | 742 | {-| -} 743 | katakanaPhoneticExtension : Generator Char 744 | katakanaPhoneticExtension = 745 | char 12784 12799 746 | 747 | 748 | {-| -} 749 | enclosedCJKLetterOrMonth : Generator Char 750 | enclosedCJKLetterOrMonth = 751 | char 12800 13055 752 | 753 | 754 | {-| -} 755 | cjkCompatibility : Generator Char 756 | cjkCompatibility = 757 | char 13056 13311 758 | 759 | 760 | {-| -} 761 | cjkUnifiedIdeographExtensionA : Generator Char 762 | cjkUnifiedIdeographExtensionA = 763 | char 13312 19903 764 | 765 | 766 | {-| -} 767 | yijingHexagramSymbol : Generator Char 768 | yijingHexagramSymbol = 769 | char 19904 19967 770 | 771 | 772 | {-| -} 773 | cjkUnifiedIdeograph : Generator Char 774 | cjkUnifiedIdeograph = 775 | char 19968 40959 776 | 777 | 778 | {-| -} 779 | yiSyllable : Generator Char 780 | yiSyllable = 781 | char 40960 42127 782 | 783 | 784 | {-| -} 785 | yiRadical : Generator Char 786 | yiRadical = 787 | char 42128 42191 788 | 789 | 790 | {-| -} 791 | lisu : Generator Char 792 | lisu = 793 | char 42192 42239 794 | 795 | 796 | {-| -} 797 | vai : Generator Char 798 | vai = 799 | char 42240 42559 800 | 801 | 802 | {-| -} 803 | cyrillicExtendedB : Generator Char 804 | cyrillicExtendedB = 805 | char 42560 42655 806 | 807 | 808 | {-| -} 809 | bamum : Generator Char 810 | bamum = 811 | char 42656 42751 812 | 813 | 814 | {-| -} 815 | modifierToneLetter : Generator Char 816 | modifierToneLetter = 817 | char 42752 42783 818 | 819 | 820 | {-| -} 821 | latinExtendedD : Generator Char 822 | latinExtendedD = 823 | char 42784 43007 824 | 825 | 826 | {-| -} 827 | sylotiNagri : Generator Char 828 | sylotiNagri = 829 | char 43008 43055 830 | 831 | 832 | {-| -} 833 | commonIndicNumberForm : Generator Char 834 | commonIndicNumberForm = 835 | char 43056 43071 836 | 837 | 838 | {-| -} 839 | phagsPa : Generator Char 840 | phagsPa = 841 | char 43072 43135 842 | 843 | 844 | {-| -} 845 | saurashtra : Generator Char 846 | saurashtra = 847 | char 43136 43231 848 | 849 | 850 | {-| -} 851 | devanagariExtended : Generator Char 852 | devanagariExtended = 853 | char 43232 43263 854 | 855 | 856 | {-| -} 857 | kayahLi : Generator Char 858 | kayahLi = 859 | char 43264 43311 860 | 861 | 862 | {-| -} 863 | rejang : Generator Char 864 | rejang = 865 | char 43312 43359 866 | 867 | 868 | {-| -} 869 | hangulJamoExtendedA : Generator Char 870 | hangulJamoExtendedA = 871 | char 43360 43391 872 | 873 | 874 | {-| -} 875 | javanese : Generator Char 876 | javanese = 877 | char 43392 43487 878 | 879 | 880 | {-| -} 881 | cham : Generator Char 882 | cham = 883 | char 43520 43615 884 | 885 | 886 | {-| -} 887 | myanmarExtendedA : Generator Char 888 | myanmarExtendedA = 889 | char 43616 43647 890 | 891 | 892 | {-| -} 893 | taiViet : Generator Char 894 | taiViet = 895 | char 43648 43743 896 | 897 | 898 | {-| -} 899 | meeteiMayekExtension : Generator Char 900 | meeteiMayekExtension = 901 | char 43744 43775 902 | 903 | 904 | {-| -} 905 | ethiopicExtendedA : Generator Char 906 | ethiopicExtendedA = 907 | char 43776 43823 908 | 909 | 910 | {-| -} 911 | meeteiMayek : Generator Char 912 | meeteiMayek = 913 | char 43968 44031 914 | 915 | 916 | {-| -} 917 | hangulSyllable : Generator Char 918 | hangulSyllable = 919 | char 44032 55215 920 | 921 | 922 | {-| -} 923 | hangulJamoExtendedB : Generator Char 924 | hangulJamoExtendedB = 925 | char 55216 55295 926 | 927 | 928 | {-| -} 929 | highSurrogate : Generator Char 930 | highSurrogate = 931 | char 55296 56191 932 | 933 | 934 | {-| -} 935 | highPrivateUseSurrogate : Generator Char 936 | highPrivateUseSurrogate = 937 | char 56192 56319 938 | 939 | 940 | {-| -} 941 | lowSurrogate : Generator Char 942 | lowSurrogate = 943 | char 56320 57343 944 | 945 | 946 | {-| -} 947 | privateUseArea : Generator Char 948 | privateUseArea = 949 | char 57344 63743 950 | 951 | 952 | {-| -} 953 | cjkCompatibilityIdeograph : Generator Char 954 | cjkCompatibilityIdeograph = 955 | char 63744 64255 956 | 957 | 958 | {-| -} 959 | alphabeticPresentationForm : Generator Char 960 | alphabeticPresentationForm = 961 | char 64256 64335 962 | 963 | 964 | {-| -} 965 | arabicPresentationFormA : Generator Char 966 | arabicPresentationFormA = 967 | char 64336 65023 968 | 969 | 970 | {-| -} 971 | variationSelector : Generator Char 972 | variationSelector = 973 | char 65024 65039 974 | 975 | 976 | {-| -} 977 | verticalForm : Generator Char 978 | verticalForm = 979 | char 65040 65055 980 | 981 | 982 | {-| -} 983 | combiningHalfMark : Generator Char 984 | combiningHalfMark = 985 | char 65056 65071 986 | 987 | 988 | {-| -} 989 | cjkCompatibilityForm : Generator Char 990 | cjkCompatibilityForm = 991 | char 65072 65103 992 | 993 | 994 | {-| -} 995 | smallFormVariant : Generator Char 996 | smallFormVariant = 997 | char 65104 65135 998 | 999 | 1000 | {-| -} 1001 | arabicPresentationFormB : Generator Char 1002 | arabicPresentationFormB = 1003 | char 65136 65279 1004 | 1005 | 1006 | {-| -} 1007 | halfwidthOrFullwidthForm : Generator Char 1008 | halfwidthOrFullwidthForm = 1009 | char 65280 65519 1010 | 1011 | 1012 | {-| -} 1013 | special : Generator Char 1014 | special = 1015 | char 65520 65535 1016 | 1017 | 1018 | {-| -} 1019 | linearBSyllable : Generator Char 1020 | linearBSyllable = 1021 | char 65536 65663 1022 | 1023 | 1024 | {-| -} 1025 | linearBIdeogram : Generator Char 1026 | linearBIdeogram = 1027 | char 65664 65791 1028 | 1029 | 1030 | {-| -} 1031 | aegeanNumber : Generator Char 1032 | aegeanNumber = 1033 | char 65792 65855 1034 | 1035 | 1036 | {-| -} 1037 | ancientGreekNumber : Generator Char 1038 | ancientGreekNumber = 1039 | char 65856 65935 1040 | 1041 | 1042 | {-| -} 1043 | ancientSymbol : Generator Char 1044 | ancientSymbol = 1045 | char 65936 65999 1046 | 1047 | 1048 | {-| -} 1049 | phaistosDisc : Generator Char 1050 | phaistosDisc = 1051 | char 66000 66047 1052 | 1053 | 1054 | {-| -} 1055 | lycian : Generator Char 1056 | lycian = 1057 | char 66176 66207 1058 | 1059 | 1060 | {-| -} 1061 | carian : Generator Char 1062 | carian = 1063 | char 66208 66271 1064 | 1065 | 1066 | {-| -} 1067 | oldItalic : Generator Char 1068 | oldItalic = 1069 | char 66304 66351 1070 | 1071 | 1072 | {-| -} 1073 | gothic : Generator Char 1074 | gothic = 1075 | char 66352 66383 1076 | 1077 | 1078 | {-| -} 1079 | ugaritic : Generator Char 1080 | ugaritic = 1081 | char 66432 66463 1082 | 1083 | 1084 | {-| -} 1085 | oldPersian : Generator Char 1086 | oldPersian = 1087 | char 66464 66527 1088 | 1089 | 1090 | {-| -} 1091 | deseret : Generator Char 1092 | deseret = 1093 | char 66560 66639 1094 | 1095 | 1096 | {-| -} 1097 | shavian : Generator Char 1098 | shavian = 1099 | char 66640 66687 1100 | 1101 | 1102 | {-| -} 1103 | osmanya : Generator Char 1104 | osmanya = 1105 | char 66688 66735 1106 | 1107 | 1108 | {-| -} 1109 | cypriotSyllable : Generator Char 1110 | cypriotSyllable = 1111 | char 67584 67647 1112 | 1113 | 1114 | {-| -} 1115 | imperialAramaic : Generator Char 1116 | imperialAramaic = 1117 | char 67648 67679 1118 | 1119 | 1120 | {-| -} 1121 | phoenician : Generator Char 1122 | phoenician = 1123 | char 67840 67871 1124 | 1125 | 1126 | {-| -} 1127 | lydian : Generator Char 1128 | lydian = 1129 | char 67872 67903 1130 | 1131 | 1132 | {-| -} 1133 | meroiticHieroglyph : Generator Char 1134 | meroiticHieroglyph = 1135 | char 67968 67999 1136 | 1137 | 1138 | {-| -} 1139 | meroiticCursive : Generator Char 1140 | meroiticCursive = 1141 | char 68000 68095 1142 | 1143 | 1144 | {-| -} 1145 | kharoshthi : Generator Char 1146 | kharoshthi = 1147 | char 68096 68191 1148 | 1149 | 1150 | {-| -} 1151 | oldSouthArabian : Generator Char 1152 | oldSouthArabian = 1153 | char 68192 68223 1154 | 1155 | 1156 | {-| -} 1157 | avestan : Generator Char 1158 | avestan = 1159 | char 68352 68415 1160 | 1161 | 1162 | {-| -} 1163 | inscriptionalParthian : Generator Char 1164 | inscriptionalParthian = 1165 | char 68416 68447 1166 | 1167 | 1168 | {-| -} 1169 | inscriptionalPahlavi : Generator Char 1170 | inscriptionalPahlavi = 1171 | char 68448 68479 1172 | 1173 | 1174 | {-| -} 1175 | oldTurkic : Generator Char 1176 | oldTurkic = 1177 | char 68608 68687 1178 | 1179 | 1180 | {-| -} 1181 | rumiNumericalSymbol : Generator Char 1182 | rumiNumericalSymbol = 1183 | char 69216 69247 1184 | 1185 | 1186 | {-| -} 1187 | brahmi : Generator Char 1188 | brahmi = 1189 | char 69632 69759 1190 | 1191 | 1192 | {-| -} 1193 | kaithi : Generator Char 1194 | kaithi = 1195 | char 69760 69839 1196 | 1197 | 1198 | {-| -} 1199 | soraSompeng : Generator Char 1200 | soraSompeng = 1201 | char 69840 69887 1202 | 1203 | 1204 | {-| -} 1205 | chakma : Generator Char 1206 | chakma = 1207 | char 69888 69967 1208 | 1209 | 1210 | {-| -} 1211 | sharada : Generator Char 1212 | sharada = 1213 | char 70016 70111 1214 | 1215 | 1216 | {-| -} 1217 | takri : Generator Char 1218 | takri = 1219 | char 71296 71375 1220 | 1221 | 1222 | {-| -} 1223 | cuneiform : Generator Char 1224 | cuneiform = 1225 | char 73728 74751 1226 | 1227 | 1228 | {-| -} 1229 | cuneiformNumberOrPunctuation : Generator Char 1230 | cuneiformNumberOrPunctuation = 1231 | char 74752 74879 1232 | 1233 | 1234 | {-| -} 1235 | egyptianHieroglyph : Generator Char 1236 | egyptianHieroglyph = 1237 | char 77824 78895 1238 | 1239 | 1240 | {-| -} 1241 | bamumSupplement : Generator Char 1242 | bamumSupplement = 1243 | char 92160 92735 1244 | 1245 | 1246 | {-| -} 1247 | miao : Generator Char 1248 | miao = 1249 | char 93952 94111 1250 | 1251 | 1252 | {-| -} 1253 | kanaSupplement : Generator Char 1254 | kanaSupplement = 1255 | char 110592 110847 1256 | 1257 | 1258 | {-| -} 1259 | byzantineMusicalSymbol : Generator Char 1260 | byzantineMusicalSymbol = 1261 | char 118784 119039 1262 | 1263 | 1264 | {-| -} 1265 | musicalSymbol : Generator Char 1266 | musicalSymbol = 1267 | char 119040 119295 1268 | 1269 | 1270 | {-| -} 1271 | ancientGreekMusicalNotationSymbol : Generator Char 1272 | ancientGreekMusicalNotationSymbol = 1273 | char 119296 119375 1274 | 1275 | 1276 | {-| -} 1277 | taiXuanJingSymbol : Generator Char 1278 | taiXuanJingSymbol = 1279 | char 119552 119647 1280 | 1281 | 1282 | {-| -} 1283 | countingRodNumeral : Generator Char 1284 | countingRodNumeral = 1285 | char 119648 119679 1286 | 1287 | 1288 | {-| -} 1289 | mathematicalAlphanumericSymbol : Generator Char 1290 | mathematicalAlphanumericSymbol = 1291 | char 119808 120831 1292 | 1293 | 1294 | {-| -} 1295 | arabicMathematicalAlphabeticSymbol : Generator Char 1296 | arabicMathematicalAlphabeticSymbol = 1297 | char 126464 126719 1298 | 1299 | 1300 | {-| -} 1301 | mahjongTile : Generator Char 1302 | mahjongTile = 1303 | char 126976 127023 1304 | 1305 | 1306 | {-| -} 1307 | dominoTile : Generator Char 1308 | dominoTile = 1309 | char 127024 127135 1310 | 1311 | 1312 | {-| -} 1313 | playingCard : Generator Char 1314 | playingCard = 1315 | char 127136 127231 1316 | 1317 | 1318 | {-| -} 1319 | enclosedAlphanumericSupplement : Generator Char 1320 | enclosedAlphanumericSupplement = 1321 | char 127232 127487 1322 | 1323 | 1324 | {-| -} 1325 | enclosedIdeographicSupplement : Generator Char 1326 | enclosedIdeographicSupplement = 1327 | char 127488 127743 1328 | 1329 | 1330 | {-| -} 1331 | miscellaneousSymbolOrPictograph : Generator Char 1332 | miscellaneousSymbolOrPictograph = 1333 | char 127744 128511 1334 | 1335 | 1336 | {-| -} 1337 | emoticon : Generator Char 1338 | emoticon = 1339 | char 128512 128591 1340 | 1341 | 1342 | {-| -} 1343 | transportOrMapSymbol : Generator Char 1344 | transportOrMapSymbol = 1345 | char 128640 128767 1346 | 1347 | 1348 | {-| -} 1349 | alchemicalSymbol : Generator Char 1350 | alchemicalSymbol = 1351 | char 128768 128895 1352 | 1353 | 1354 | {-| -} 1355 | cjkUnifiedIdeographExtensionB : Generator Char 1356 | cjkUnifiedIdeographExtensionB = 1357 | char 131072 173791 1358 | 1359 | 1360 | {-| -} 1361 | cjkUnifiedIdeographExtensionC : Generator Char 1362 | cjkUnifiedIdeographExtensionC = 1363 | char 173824 177983 1364 | 1365 | 1366 | {-| -} 1367 | cjkUnifiedIdeographExtensionD : Generator Char 1368 | cjkUnifiedIdeographExtensionD = 1369 | char 177984 178207 1370 | 1371 | 1372 | {-| -} 1373 | cjkCompatibilityIdeographSupplement : Generator Char 1374 | cjkCompatibilityIdeographSupplement = 1375 | char 194560 195103 1376 | 1377 | 1378 | {-| -} 1379 | tag : Generator Char 1380 | tag = 1381 | char 917504 917631 1382 | 1383 | 1384 | {-| -} 1385 | variationSelectorSupplement : Generator Char 1386 | variationSelectorSupplement = 1387 | char 917760 917999 1388 | 1389 | 1390 | {-| -} 1391 | supplementaryPrivateUseAreaA : Generator Char 1392 | supplementaryPrivateUseAreaA = 1393 | char 983040 1048575 1394 | 1395 | 1396 | {-| -} 1397 | supplementaryPrivateUseAreaB : Generator Char 1398 | supplementaryPrivateUseAreaB = 1399 | char 1048576 1114111 1400 | -------------------------------------------------------------------------------- /src/Random/Date.elm: -------------------------------------------------------------------------------- 1 | module Random.Date exposing (weekday, month) 2 | 3 | {-| Extra randomized functions on dates (see `elm/time`). 4 | 5 | We only provide generators for days and months. Other generators are trivial for you to implement yourself and can be made specific to your needs. 6 | 7 | 8 | # Generators 9 | 10 | @docs weekday, month 11 | 12 | -} 13 | 14 | import Random exposing (Generator, float, int, map) 15 | import Random.Extra exposing (sample) 16 | import Time exposing (Month(..), Weekday(..)) 17 | 18 | 19 | {-| Generate a random day of the week. 20 | -} 21 | weekday : Generator Weekday 22 | weekday = 23 | sample 24 | [ Mon 25 | , Tue 26 | , Wed 27 | , Thu 28 | , Fri 29 | , Sat 30 | , Sun 31 | ] 32 | |> map (Maybe.withDefault Mon) 33 | 34 | 35 | {-| Generate a random month of the year. 36 | -} 37 | month : Generator Month 38 | month = 39 | sample 40 | [ Jan 41 | , Feb 42 | , Mar 43 | , Apr 44 | , May 45 | , Jun 46 | , Jul 47 | , Aug 48 | , Sep 49 | , Oct 50 | , Nov 51 | , Dec 52 | ] 53 | |> map (Maybe.withDefault Jan) 54 | -------------------------------------------------------------------------------- /src/Random/Dict.elm: -------------------------------------------------------------------------------- 1 | module Random.Dict exposing (dict, rangeLengthDict) 2 | 3 | {-| Extra randomized functions on dicts. 4 | 5 | 6 | # Generators 7 | 8 | @docs dict, rangeLengthDict 9 | 10 | -} 11 | 12 | import Dict exposing (Dict, fromList) 13 | import Random exposing (Generator, andThen, int, list, map, pair) 14 | 15 | 16 | {-| Generate a random dict with given length, key generator, and value generator 17 | 18 | randomLength10StringIntDict = 19 | dict 10 (englishWord 10) (int 0 100) 20 | 21 | -} 22 | dict : Int -> Generator comparable -> Generator value -> Generator (Dict comparable value) 23 | dict dictLength keyGenerator valueGenerator = 24 | map fromList (list dictLength (pair keyGenerator valueGenerator)) 25 | 26 | 27 | {-| Generate a random dict of random length given a minimum length and 28 | a maximum length. 29 | -} 30 | rangeLengthDict : Int -> Int -> Generator comparable -> Generator value -> Generator (Dict comparable value) 31 | rangeLengthDict minLength maxLength keyGenerator valueGenerator = 32 | andThen (\len -> dict len keyGenerator valueGenerator) (int minLength maxLength) 33 | -------------------------------------------------------------------------------- /src/Random/Extra.elm: -------------------------------------------------------------------------------- 1 | module Random.Extra exposing 2 | ( bool 3 | , map6, andMap 4 | , oneIn, maybe, result, choice 5 | , sequence, traverse, choices, frequency, sample, combine, rangeLengthList 6 | , filter 7 | , andThen2, andThen3, andThen4, andThen5, andThen6 8 | ) 9 | 10 | {-| This module provides many common and general-purpose helper functions for 11 | core's Random library. You can find even more useful functions for a particular 12 | type in the other modules. 13 | 14 | 15 | # Values 16 | 17 | @docs bool 18 | 19 | 20 | # Maps 21 | 22 | For `map` and `mapN` up through N=5, use the core library. 23 | 24 | @docs map6, andMap 25 | 26 | 27 | # New Generators 28 | 29 | @docs oneIn, maybe, result, choice 30 | 31 | 32 | # Working with Lists 33 | 34 | @docs sequence, traverse, choices, frequency, sample, combine, rangeLengthList 35 | 36 | 37 | # Filtered Generators 38 | 39 | @docs filter 40 | 41 | 42 | # andThenN 43 | 44 | These functions are like `mapN` except the function you pass in does not return 45 | an exact value, but instead another generator. That means you can take in several 46 | random arguments to drive more randomness. 47 | 48 | @docs andThen2, andThen3, andThen4, andThen5, andThen6 49 | 50 | -} 51 | 52 | import Random exposing (Generator, andThen, constant, float, int, list, map, step) 53 | 54 | 55 | {-| An unbiased generator of `Bool` values. 56 | -} 57 | bool : Generator Bool 58 | bool = 59 | Random.uniform True [ False ] 60 | 61 | 62 | {-| Map a function of six arguments over six generators. 63 | -} 64 | map6 : (a -> b -> c -> d -> e -> f -> g) -> Generator a -> Generator b -> Generator c -> Generator d -> Generator e -> Generator f -> Generator g 65 | map6 f generatorA generatorB generatorC generatorD generatorE generatorF = 66 | Random.map5 f generatorA generatorB generatorC generatorD generatorE |> andMap generatorF 67 | 68 | 69 | {-| Map over any number of generators. 70 | 71 | type alias Person = -- some large record 72 | 73 | randomPerson : Generator Person 74 | randomPerson = 75 | map Person genFirstName 76 | |> andMap genLastName 77 | |> andMap genBirthday 78 | |> andMap genPhoneNumber 79 | |> andMap genAddress 80 | |> andMap genEmail 81 | 82 | -} 83 | andMap : Generator a -> Generator (a -> b) -> Generator b 84 | andMap = 85 | Random.map2 (|>) 86 | 87 | 88 | {-| Filter a generator so that all generated values satisfy the given predicate. 89 | 90 | evens : Generator Int 91 | evens = 92 | filter (\i -> i % 2 == 0) (int minInt maxInt) 93 | 94 | **Warning:** If the predicate is unsatisfiable, the generator will not 95 | terminate, your application will crash with a stack overflow, and you will be 96 | sad. You should also avoid predicates that are merely very difficult to satisfy. 97 | 98 | badCrashingGenerator = 99 | filter (\_ -> False) anotherGenerator 100 | 101 | likelyCrashingGenerator = 102 | filter (\i -> i % 2000 == 0) (int minInt maxInt) 103 | 104 | -} 105 | filter : (a -> Bool) -> Generator a -> Generator a 106 | filter predicate generator = 107 | generator 108 | |> andThen 109 | (\a -> 110 | if predicate a then 111 | constant a 112 | 113 | else 114 | filter predicate generator 115 | ) 116 | 117 | 118 | {-| Produce `True` one-in-n times on average. 119 | 120 | Do not pass a value less then one to this function. 121 | 122 | flippedHeads = 123 | oneIn 2 124 | 125 | rolled6 = 126 | oneIn 6 127 | 128 | -} 129 | oneIn : Int -> Generator Bool 130 | oneIn n = 131 | map ((==) 1) (int 1 n) 132 | 133 | 134 | {-| Choose between two values with equal probability. 135 | 136 | type Flip 137 | = Heads 138 | | Tails 139 | 140 | coinFlip : Generator Flip 141 | coinFlip = 142 | choice Heads Tails 143 | 144 | Note that this function takes values, not generators. That's because it's meant 145 | to be a lightweight helper for a specific use. If you need to choose between two 146 | generators, use `choices [gen1, gen2]`. 147 | 148 | -} 149 | choice : a -> a -> Generator a 150 | choice x y = 151 | map 152 | (\b -> 153 | if b then 154 | x 155 | 156 | else 157 | y 158 | ) 159 | bool 160 | 161 | 162 | {-| Start with a list of generators, and turn them into a generator that returns a list. 163 | -} 164 | sequence : List (Generator a) -> Generator (List a) 165 | sequence = 166 | List.foldr (Random.map2 (::)) (Random.constant []) 167 | 168 | 169 | {-| Apply a function that returns a generator to each element of a list, 170 | and turn it into a generator that returns a list. 171 | -} 172 | traverse : (a -> Generator b) -> List a -> Generator (List b) 173 | traverse f = 174 | sequence << List.map f 175 | 176 | 177 | {-| Create a generator that chooses a generator from a list of generators 178 | with equal probability. 179 | 180 | We guarantee a nonempty list is passed by splitting it into two arguments. 181 | 182 | -} 183 | choices : Generator a -> List (Generator a) -> Generator a 184 | choices hd gens = 185 | frequency ( 1, hd ) <| List.map (\g -> ( 1, g )) gens 186 | 187 | 188 | {-| Create a generator that chooses a generator from a list of generators 189 | based on the provided weight. The likelihood of a given generator being 190 | chosen is its weight divided by the total weight (which doesn't have to equal 1). 191 | 192 | We guarantee a nonempty list is passed by splitting it into two arguments. 193 | 194 | -} 195 | frequency : ( Float, Generator a ) -> List ( Float, Generator a ) -> Generator a 196 | frequency head pairs = 197 | let 198 | total = 199 | List.sum <| List.map (abs << Tuple.first) (head :: pairs) 200 | 201 | pick someChoices n = 202 | case someChoices of 203 | ( k, g ) :: rest -> 204 | if n <= k then 205 | g 206 | 207 | else 208 | pick rest (n - k) 209 | 210 | -- this should never happen 211 | _ -> 212 | Tuple.second head 213 | in 214 | float 0 total |> andThen (pick (head :: pairs)) 215 | 216 | 217 | {-| Turn a list of generators into a generator of lists. 218 | -} 219 | combine : List (Generator a) -> Generator (List a) 220 | combine generators = 221 | case generators of 222 | [] -> 223 | constant [] 224 | 225 | g :: gs -> 226 | Random.map2 (::) g (combine gs) 227 | 228 | 229 | {-| Given a list, choose an element uniformly at random. `Nothing` is only 230 | produced if the list is empty. 231 | 232 | type Direction 233 | = North 234 | | South 235 | | East 236 | | West 237 | 238 | direction : Generator Direction 239 | direction = 240 | sample [ North, South, East, West ] 241 | |> map (Maybe.withDefault North) 242 | 243 | -} 244 | sample : List a -> Generator (Maybe a) 245 | sample = 246 | let 247 | find k ys = 248 | case ys of 249 | [] -> 250 | Nothing 251 | 252 | z :: zs -> 253 | if k == 0 then 254 | Just z 255 | 256 | else 257 | find (k - 1) zs 258 | in 259 | \xs -> map (\i -> find i xs) (int 0 (List.length xs - 1)) 260 | 261 | 262 | {-| Produce `Just` a value on `True`, and `Nothing` on `False`. 263 | 264 | You can use `bool` or `oneIn n` for the first argument. 265 | 266 | -} 267 | maybe : Generator Bool -> Generator a -> Generator (Maybe a) 268 | maybe genBool genA = 269 | genBool 270 | |> andThen 271 | (\b -> 272 | if b then 273 | map Just genA 274 | 275 | else 276 | constant Nothing 277 | ) 278 | 279 | 280 | {-| Produce an `Ok` a value on `True`, and an `Err` value on `False`. 281 | 282 | You can use `bool` or `oneIn n` for the first argument. 283 | 284 | -} 285 | result : Generator Bool -> Generator err -> Generator val -> Generator (Result err val) 286 | result genBool genErr genVal = 287 | genBool 288 | |> andThen 289 | (\b -> 290 | if b then 291 | map Ok genVal 292 | 293 | else 294 | map Err genErr 295 | ) 296 | 297 | 298 | {-| Generate a random list of random length given a minimum length and 299 | a maximum length. 300 | -} 301 | rangeLengthList : Int -> Int -> Generator a -> Generator (List a) 302 | rangeLengthList minLength maxLength generator = 303 | andThen (\len -> list len generator) (int minLength maxLength) 304 | 305 | 306 | {-| -} 307 | andThen2 : (a -> b -> Generator c) -> Generator a -> Generator b -> Generator c 308 | andThen2 constructor generatorA generatorB = 309 | generatorA 310 | |> andThen 311 | (\a -> 312 | generatorB 313 | |> andThen 314 | (\b -> 315 | constructor a b 316 | ) 317 | ) 318 | 319 | 320 | {-| -} 321 | andThen3 : (a -> b -> c -> Generator d) -> Generator a -> Generator b -> Generator c -> Generator d 322 | andThen3 constructor generatorA generatorB generatorC = 323 | generatorA 324 | |> andThen 325 | (\a -> 326 | generatorB 327 | |> andThen 328 | (\b -> 329 | generatorC 330 | |> andThen 331 | (\c -> 332 | constructor a b c 333 | ) 334 | ) 335 | ) 336 | 337 | 338 | {-| -} 339 | andThen4 : (a -> b -> c -> d -> Generator e) -> Generator a -> Generator b -> Generator c -> Generator d -> Generator e 340 | andThen4 constructor generatorA generatorB generatorC generatorD = 341 | generatorA 342 | |> andThen 343 | (\a -> 344 | generatorB 345 | |> andThen 346 | (\b -> 347 | generatorC 348 | |> andThen 349 | (\c -> 350 | generatorD 351 | |> andThen 352 | (\d -> 353 | constructor a b c d 354 | ) 355 | ) 356 | ) 357 | ) 358 | 359 | 360 | {-| -} 361 | andThen5 : (a -> b -> c -> d -> e -> Generator f) -> Generator a -> Generator b -> Generator c -> Generator d -> Generator e -> Generator f 362 | andThen5 constructor generatorA generatorB generatorC generatorD generatorE = 363 | generatorA 364 | |> andThen 365 | (\a -> 366 | generatorB 367 | |> andThen 368 | (\b -> 369 | generatorC 370 | |> andThen 371 | (\c -> 372 | generatorD 373 | |> andThen 374 | (\d -> 375 | generatorE 376 | |> andThen 377 | (\e -> 378 | constructor a b c d e 379 | ) 380 | ) 381 | ) 382 | ) 383 | ) 384 | 385 | 386 | {-| -} 387 | andThen6 : (a -> b -> c -> d -> e -> f -> Generator g) -> Generator a -> Generator b -> Generator c -> Generator d -> Generator e -> Generator f -> Generator g 388 | andThen6 constructor generatorA generatorB generatorC generatorD generatorE generatorF = 389 | generatorA 390 | |> andThen 391 | (\a -> 392 | generatorB 393 | |> andThen 394 | (\b -> 395 | generatorC 396 | |> andThen 397 | (\c -> 398 | generatorD 399 | |> andThen 400 | (\d -> 401 | generatorE 402 | |> andThen 403 | (\e -> 404 | generatorF 405 | |> andThen 406 | (\f -> 407 | constructor a b c d e f 408 | ) 409 | ) 410 | ) 411 | ) 412 | ) 413 | ) 414 | -------------------------------------------------------------------------------- /src/Random/Float.elm: -------------------------------------------------------------------------------- 1 | module Random.Float exposing 2 | ( anyFloat, positiveFloat, negativeFloat, floatGreaterThan, floatLessThan 3 | , normal, standardNormal 4 | ) 5 | 6 | {-| Extra randomized functions on floats. 7 | 8 | 9 | # Arithmetic Generators 10 | 11 | @docs anyFloat, positiveFloat, negativeFloat, floatGreaterThan, floatLessThan 12 | 13 | 14 | # Gaussian Generators 15 | 16 | @docs normal, standardNormal 17 | 18 | -} 19 | 20 | import Random exposing (Generator, float, map, maxInt, minInt) 21 | 22 | 23 | {-| A generator that generates any float 24 | -} 25 | anyFloat : Generator Float 26 | anyFloat = 27 | float (toFloat minInt) (toFloat maxInt) 28 | 29 | 30 | {-| A generator that generates any positive float 31 | -} 32 | positiveFloat : Generator Float 33 | positiveFloat = 34 | float 0 (toFloat maxInt) 35 | 36 | 37 | {-| A generator that generates any negative float 38 | -} 39 | negativeFloat : Generator Float 40 | negativeFloat = 41 | float (toFloat minInt) 0 42 | 43 | 44 | {-| A generator that generates a float greater than a given float 45 | -} 46 | floatGreaterThan : Float -> Generator Float 47 | floatGreaterThan value = 48 | float value (toFloat maxInt) 49 | 50 | 51 | {-| A generator that generates a float less than a given float 52 | -} 53 | floatLessThan : Float -> Generator Float 54 | floatLessThan value = 55 | float (toFloat minInt) value 56 | 57 | 58 | {-| Create a generator of floats that is normally distributed with 59 | given mean and standard deviation. 60 | -} 61 | normal : Float -> Float -> Generator Float 62 | normal mean stdDev = 63 | map (\u -> u * stdDev + mean) standardNormal 64 | 65 | 66 | {-| A generator that follows a standard normal distribution (as opposed to 67 | a uniform distribution) 68 | -} 69 | standardNormal : Generator Float 70 | standardNormal = 71 | Random.map2 72 | (\u theta -> sqrt (-2 * logBase e (1 - max 0 u)) * cos theta) 73 | (float 0 1) 74 | (float 0 (2 * pi)) 75 | -------------------------------------------------------------------------------- /src/Random/Int.elm: -------------------------------------------------------------------------------- 1 | module Random.Int exposing (anyInt, positiveInt, negativeInt, intGreaterThan, intLessThan) 2 | 3 | {-| Extra randomized functions on ints. 4 | 5 | 6 | # Generators 7 | 8 | @docs anyInt, positiveInt, negativeInt, intGreaterThan, intLessThan 9 | 10 | -} 11 | 12 | import Random exposing (Generator, int, maxInt, minInt) 13 | 14 | 15 | {-| A generator that generates any int that can be generated by the 16 | random generator algorithm. 17 | -} 18 | anyInt : Generator Int 19 | anyInt = 20 | int minInt maxInt 21 | 22 | 23 | {-| A generator that generates a positive int 24 | -} 25 | positiveInt : Generator Int 26 | positiveInt = 27 | int 1 maxInt 28 | 29 | 30 | {-| A generator that generates a negative int 31 | -} 32 | negativeInt : Generator Int 33 | negativeInt = 34 | int minInt -1 35 | 36 | 37 | {-| A generator that generates an int greater than a given int 38 | -} 39 | intGreaterThan : Int -> Generator Int 40 | intGreaterThan value = 41 | int (value + 1) maxInt 42 | 43 | 44 | {-| A generator that generates an int less than a given int 45 | -} 46 | intLessThan : Int -> Generator Int 47 | intLessThan value = 48 | int minInt (value - 1) 49 | -------------------------------------------------------------------------------- /src/Random/List.elm: -------------------------------------------------------------------------------- 1 | module Random.List exposing (choose, shuffle, choices) 2 | 3 | {-| Extra randomized functions on lists. 4 | 5 | 6 | # Work with a List 7 | 8 | @docs choose, shuffle, choices 9 | 10 | -} 11 | 12 | import Random exposing (Generator, andThen, constant) 13 | 14 | 15 | {-| Get nth element of the list. If the list is empty, the selected element 16 | will be `Nothing`. 17 | -} 18 | get : Int -> List a -> Maybe a 19 | get index list = 20 | list 21 | |> List.drop index 22 | |> List.head 23 | 24 | 25 | {-| Sample without replacement: produce a randomly selected element of the 26 | list, and the list with that element omitted. If the list is empty, the 27 | selected element will be `Nothing`. 28 | -} 29 | choose : List a -> Generator ( Maybe a, List a ) 30 | choose list = 31 | if List.isEmpty list then 32 | constant ( Nothing, list ) 33 | 34 | else 35 | let 36 | lastIndex = 37 | List.length list - 1 38 | 39 | front i = 40 | List.take i list 41 | 42 | back i = 43 | List.drop (i + 1) list 44 | 45 | gen = 46 | Random.int 0 lastIndex 47 | in 48 | Random.map 49 | (\index -> 50 | ( get index list, List.append (front index) (back index) ) 51 | ) 52 | gen 53 | 54 | 55 | {-| Repeated sample without replacement: produce a list of randomly 56 | selected elements of some list, and the list of unselected elements. 57 | -} 58 | choices : Int -> List a -> Generator ( List a, List a ) 59 | choices count list = 60 | if count < 1 then 61 | constant ( [], list ) 62 | 63 | else 64 | choose list 65 | |> andThen 66 | (\( choice, remaining ) -> 67 | let 68 | genRest = 69 | Random.lazy (\_ -> choices (count - 1) remaining) 70 | 71 | addToChoices = 72 | \elem ( chosen, unchosen ) -> ( elem :: chosen, unchosen ) 73 | in 74 | case choice of 75 | Nothing -> 76 | constant ( [], list ) 77 | 78 | Just elem -> 79 | Random.map (addToChoices elem) genRest 80 | ) 81 | 82 | 83 | anyInt : Generator Int 84 | anyInt = 85 | Random.int Random.minInt Random.maxInt 86 | 87 | 88 | {-| Shuffle the list. Takes O(_n_ log _n_) time and no extra space. 89 | -} 90 | shuffle : List a -> Generator (List a) 91 | shuffle list = 92 | Random.map 93 | (\independentSeed -> 94 | list 95 | |> List.foldl 96 | (\item ( acc, seed ) -> 97 | let 98 | ( tag, nextSeed ) = 99 | Random.step anyInt seed 100 | in 101 | ( ( item, tag ) :: acc, nextSeed ) 102 | ) 103 | ( [], independentSeed ) 104 | |> Tuple.first 105 | |> List.sortBy Tuple.second 106 | |> List.map Tuple.first 107 | ) 108 | Random.independentSeed 109 | -------------------------------------------------------------------------------- /src/Random/Order.elm: -------------------------------------------------------------------------------- 1 | module Random.Order exposing (order) 2 | 3 | {-| An extra random generator for the `Order` type. 4 | 5 | @docs order 6 | 7 | -} 8 | 9 | import Random exposing (Generator, map) 10 | import Random.Extra exposing (sample) 11 | 12 | 13 | {-| Generate a random order with equal probability. 14 | -} 15 | order : Generator Order 16 | order = 17 | sample 18 | [ LT 19 | , EQ 20 | , GT 21 | ] 22 | |> map (Maybe.withDefault EQ) 23 | -------------------------------------------------------------------------------- /src/Random/Set.elm: -------------------------------------------------------------------------------- 1 | module Random.Set exposing 2 | ( set 3 | , sample 4 | , notInSet 5 | ) 6 | 7 | {-| Extra randomized functions on sets. 8 | 9 | 10 | # Create a Set 11 | 12 | @docs set 13 | 14 | 15 | # Create a Generator 16 | 17 | @docs sample 18 | 19 | 20 | # Modify a Generator 21 | 22 | @docs notInSet 23 | 24 | -} 25 | 26 | import Random exposing (Generator, andThen, constant, map) 27 | import Random.Extra exposing (filter) 28 | import Set exposing (Set) 29 | 30 | 31 | {-| Filter a generator of all values not in a given set. 32 | -} 33 | notInSet : Set comparable -> Generator comparable -> Generator comparable 34 | notInSet aSet generator = 35 | filter (\element -> not <| Set.member element aSet) generator 36 | 37 | 38 | {-| Select a value from a set uniformly at random, or `Nothing` for an empty set. 39 | Analogous to `Random.Extra.sample` but with sets. 40 | -} 41 | sample : Set comparable -> Generator (Maybe comparable) 42 | sample aSet = 43 | Random.Extra.sample (Set.toList aSet) 44 | 45 | 46 | {-| Generate a set of at most the given size from a generator. 47 | 48 | The size of a generated set is limited both by the integer provided and the 49 | number of unique values the generator can produce. It is very likely, but not 50 | guaranteed, that generated sets will be as big as the smaller of these two limits. 51 | 52 | -} 53 | set : Int -> Generator comparable -> Generator (Set comparable) 54 | set maxLength generator = 55 | let 56 | helper aSet remaining strikes = 57 | if remaining <= 0 || strikes == 10 then 58 | constant aSet 59 | 60 | else 61 | generator 62 | |> andThen 63 | (\val -> 64 | let 65 | newSet = 66 | Set.insert val aSet 67 | in 68 | if Set.size newSet == Set.size aSet then 69 | helper aSet remaining (strikes + 1) 70 | 71 | else 72 | helper newSet (remaining - 1) 0 73 | ) 74 | in 75 | helper Set.empty maxLength 0 76 | -------------------------------------------------------------------------------- /src/Random/String.elm: -------------------------------------------------------------------------------- 1 | module Random.String exposing (string, rangeLengthString) 2 | 3 | {-| Extra randomized functions on strings. 4 | 5 | 6 | # Create a String 7 | 8 | @docs string, rangeLengthString 9 | 10 | -} 11 | 12 | import Random exposing (Generator, andThen, int, list, map, map2) 13 | import String exposing (fromList) 14 | 15 | 16 | {-| Generate a random string of a given length with a given character generator 17 | 18 | fiveLetterEnglishWord = 19 | string 5 Random.Char.english 20 | 21 | -} 22 | string : Int -> Generator Char -> Generator String 23 | string stringLength charGenerator = 24 | map fromList (list stringLength charGenerator) 25 | 26 | 27 | {-| Generates a random string of random length given the minimum length 28 | and maximum length and a given character generator. 29 | -} 30 | rangeLengthString : Int -> Int -> Generator Char -> Generator String 31 | rangeLengthString minLength maxLength charGenerator = 32 | andThen (\len -> string len charGenerator) (int minLength maxLength) 33 | -------------------------------------------------------------------------------- /tests/Tests/Random/Array.elm: -------------------------------------------------------------------------------- 1 | module Tests.Random.Array exposing (suite) 2 | 3 | import Array 4 | import Expect 5 | import Fuzz 6 | import Random 7 | import Random.Array 8 | import Set 9 | import Test exposing (Test) 10 | 11 | 12 | suite : Test 13 | suite = 14 | Test.describe "shuffle" 15 | [ Test.test "shuffle 10 elements with a given seedRoot" <| 16 | \() -> 17 | let 18 | initialList = 19 | List.range 0 9 20 | 21 | ( shuffledArray, _ ) = 22 | Random.step (Random.Array.shuffle (Array.fromList initialList)) (Random.initialSeed 0) 23 | in 24 | shuffledArray 25 | |> Array.toList 26 | |> Expect.equalLists [ 7, 6, 2, 8, 1, 4, 9, 5, 0, 3 ] 27 | 28 | -- 29 | , Test.fuzz (Fuzz.tuple ( Fuzz.int, Fuzz.intRange 0 100 )) "test existing all of the shuffled elements" <| 30 | \( seedRoot, listLength ) -> 31 | let 32 | initialList = 33 | List.range 0 listLength 34 | 35 | ( shuffledArray, _ ) = 36 | Random.step (Random.Array.shuffle (Array.fromList initialList)) (Random.initialSeed seedRoot) 37 | in 38 | shuffledArray 39 | |> Array.toList 40 | |> List.sort 41 | |> Expect.equalLists initialList 42 | 43 | -- 44 | , Test.fuzz (Fuzz.tuple ( Fuzz.int, Fuzz.intRange 0 100 )) "test uniq of the shuffled elements" <| 45 | \( seedRoot, listLength ) -> 46 | let 47 | initialList = 48 | List.range 0 listLength 49 | 50 | ( shuffledArray, _ ) = 51 | Random.step (Random.Array.shuffle (Array.fromList initialList)) (Random.initialSeed seedRoot) 52 | in 53 | shuffledArray 54 | |> Array.toList 55 | |> Set.fromList 56 | |> Set.diff (Set.fromList initialList) 57 | |> Expect.equalSets Set.empty 58 | 59 | -- 60 | , Test.fuzzWith { runs = 1 } Fuzz.int "critical 100k length" <| 61 | \seedRoot -> 62 | let 63 | initialList = 64 | List.range 0 100000 65 | 66 | ( shuffledArray, _ ) = 67 | Random.step (Random.Array.shuffle (Array.fromList initialList)) (Random.initialSeed seedRoot) 68 | in 69 | shuffledArray 70 | |> Array.toList 71 | |> List.sort 72 | |> Expect.equalLists initialList 73 | ] 74 | -------------------------------------------------------------------------------- /tests/Tests/Random/Extra.elm: -------------------------------------------------------------------------------- 1 | module Tests.Random.Extra exposing (sequenceTest) 2 | 3 | import Expect 4 | import Fuzz 5 | import Random 6 | import Random.Extra as RE 7 | import Test exposing (Test) 8 | 9 | 10 | {-| This library did not originally have tests, so the tests below have been added with the functions 11 | that they test. 12 | 13 | If you want to add tests, please open a PR! Even so-so tests are better than no tests. 14 | 15 | -} 16 | sequenceTest : Test 17 | sequenceTest = 18 | Test.describe "Random.Extra.sequence" 19 | [ Test.test "it runs the generators in the correct order" <| 20 | \() -> 21 | [ Random.constant 0, Random.constant 1 ] 22 | |> RE.sequence 23 | |> (\gen -> Random.step gen (Random.initialSeed 42)) 24 | |> Tuple.first 25 | |> Expect.equalLists [ 0, 1 ] 26 | ] 27 | -------------------------------------------------------------------------------- /tests/Tests/Random/List.elm: -------------------------------------------------------------------------------- 1 | module Tests.Random.List exposing (suite) 2 | 3 | import Expect 4 | import Fuzz 5 | import Random 6 | import Random.List 7 | import Set 8 | import Test exposing (Test) 9 | 10 | 11 | suite : Test 12 | suite = 13 | Test.describe "shuffle" 14 | [ Test.test "shuffle 10 elements with a given seedRoot" <| 15 | \() -> 16 | let 17 | initialList = 18 | List.range 0 9 19 | 20 | ( shuffledList, _ ) = 21 | Random.step (Random.List.shuffle initialList) (Random.initialSeed 0) 22 | in 23 | shuffledList 24 | |> Expect.equalLists [ 7, 6, 2, 8, 1, 4, 9, 5, 0, 3 ] 25 | 26 | -- 27 | , Test.fuzz (Fuzz.tuple ( Fuzz.int, Fuzz.intRange 0 100 )) "test existing all of the shuffled elements" <| 28 | \( seedRoot, listLength ) -> 29 | let 30 | initialList = 31 | List.range 0 listLength 32 | 33 | ( shuffledList, _ ) = 34 | Random.step (Random.List.shuffle initialList) (Random.initialSeed seedRoot) 35 | in 36 | shuffledList 37 | |> List.sort 38 | |> Expect.equalLists initialList 39 | 40 | -- 41 | , Test.fuzz (Fuzz.tuple ( Fuzz.int, Fuzz.intRange 0 100 )) "test uniq of the shuffled elements" <| 42 | \( seedRoot, listLength ) -> 43 | let 44 | initialList = 45 | List.range 0 listLength 46 | 47 | ( shuffledList, _ ) = 48 | Random.step (Random.List.shuffle initialList) (Random.initialSeed seedRoot) 49 | in 50 | shuffledList 51 | |> Set.fromList 52 | |> Set.diff (Set.fromList initialList) 53 | |> Expect.equalSets Set.empty 54 | 55 | -- 56 | , Test.fuzzWith { runs = 1 } Fuzz.int "critical 100k length" <| 57 | \seedRoot -> 58 | let 59 | initialList = 60 | List.range 0 100000 61 | 62 | ( shuffledList, _ ) = 63 | Random.step (Random.List.shuffle initialList) (Random.initialSeed seedRoot) 64 | in 65 | shuffledList 66 | |> List.sort 67 | |> Expect.equalLists initialList 68 | ] 69 | --------------------------------------------------------------------------------