rbs-relaxed 3.9.0.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +7 -0
- data/.github/dependabot.yml +22 -0
- data/.github/workflows/comments.yml +35 -0
- data/.github/workflows/dependabot.yml +30 -0
- data/.github/workflows/ruby.yml +82 -0
- data/.github/workflows/typecheck.yml +38 -0
- data/.github/workflows/windows.yml +43 -0
- data/.gitignore +23 -0
- data/.rubocop.yml +68 -0
- data/BSDL +22 -0
- data/CHANGELOG.md +1868 -0
- data/COPYING +56 -0
- data/README.md +203 -0
- data/Rakefile +417 -0
- data/Steepfile +44 -0
- data/config.yml +313 -0
- data/core/array.rbs +4062 -0
- data/core/basic_object.rbs +375 -0
- data/core/binding.rbs +150 -0
- data/core/builtin.rbs +277 -0
- data/core/class.rbs +220 -0
- data/core/comparable.rbs +171 -0
- data/core/complex.rbs +786 -0
- data/core/constants.rbs +96 -0
- data/core/data.rbs +415 -0
- data/core/dir.rbs +981 -0
- data/core/encoding.rbs +1371 -0
- data/core/enumerable.rbs +2405 -0
- data/core/enumerator/product.rbs +92 -0
- data/core/enumerator.rbs +630 -0
- data/core/env.rbs +6 -0
- data/core/errno.rbs +673 -0
- data/core/errors.rbs +760 -0
- data/core/exception.rbs +485 -0
- data/core/false_class.rbs +82 -0
- data/core/fiber.rbs +550 -0
- data/core/fiber_error.rbs +11 -0
- data/core/file.rbs +2936 -0
- data/core/file_test.rbs +331 -0
- data/core/float.rbs +1151 -0
- data/core/gc.rbs +644 -0
- data/core/global_variables.rbs +184 -0
- data/core/hash.rbs +1861 -0
- data/core/integer.rbs +1413 -0
- data/core/io/buffer.rbs +984 -0
- data/core/io/wait.rbs +70 -0
- data/core/io.rbs +3406 -0
- data/core/kernel.rbs +3096 -0
- data/core/marshal.rbs +207 -0
- data/core/match_data.rbs +635 -0
- data/core/math.rbs +729 -0
- data/core/method.rbs +386 -0
- data/core/module.rbs +1704 -0
- data/core/nil_class.rbs +209 -0
- data/core/numeric.rbs +818 -0
- data/core/object.rbs +110 -0
- data/core/object_space/weak_key_map.rbs +166 -0
- data/core/object_space.rbs +190 -0
- data/core/proc.rbs +868 -0
- data/core/process.rbs +2296 -0
- data/core/ractor.rbs +1068 -0
- data/core/random.rbs +237 -0
- data/core/range.rbs +1107 -0
- data/core/rational.rbs +531 -0
- data/core/rb_config.rbs +88 -0
- data/core/rbs/unnamed/argf.rbs +1229 -0
- data/core/rbs/unnamed/env_class.rbs +1209 -0
- data/core/rbs/unnamed/random.rbs +293 -0
- data/core/refinement.rbs +59 -0
- data/core/regexp.rbs +1930 -0
- data/core/ruby_vm.rbs +765 -0
- data/core/rubygems/basic_specification.rbs +6 -0
- data/core/rubygems/config_file.rbs +38 -0
- data/core/rubygems/dependency_installer.rbs +6 -0
- data/core/rubygems/errors.rbs +176 -0
- data/core/rubygems/installer.rbs +15 -0
- data/core/rubygems/path_support.rbs +6 -0
- data/core/rubygems/platform.rbs +7 -0
- data/core/rubygems/request_set.rbs +49 -0
- data/core/rubygems/requirement.rbs +148 -0
- data/core/rubygems/rubygems.rbs +1171 -0
- data/core/rubygems/source_list.rbs +15 -0
- data/core/rubygems/specification.rbs +23 -0
- data/core/rubygems/stream_ui.rbs +5 -0
- data/core/rubygems/uninstaller.rbs +10 -0
- data/core/rubygems/version.rbs +294 -0
- data/core/set.rbs +621 -0
- data/core/signal.rbs +100 -0
- data/core/string.rbs +3583 -0
- data/core/struct.rbs +667 -0
- data/core/symbol.rbs +475 -0
- data/core/thread.rbs +1765 -0
- data/core/thread_group.rbs +79 -0
- data/core/time.rbs +1762 -0
- data/core/trace_point.rbs +477 -0
- data/core/true_class.rbs +98 -0
- data/core/unbound_method.rbs +329 -0
- data/core/warning.rbs +87 -0
- data/docs/CONTRIBUTING.md +106 -0
- data/docs/architecture.md +110 -0
- data/docs/collection.md +192 -0
- data/docs/data_and_struct.md +86 -0
- data/docs/gem.md +57 -0
- data/docs/rbs_by_example.md +309 -0
- data/docs/repo.md +125 -0
- data/docs/sigs.md +167 -0
- data/docs/stdlib.md +147 -0
- data/docs/syntax.md +910 -0
- data/docs/tools.md +17 -0
- data/exe/rbs +7 -0
- data/ext/rbs_extension/extconf.rb +15 -0
- data/ext/rbs_extension/lexer.c +2728 -0
- data/ext/rbs_extension/lexer.h +179 -0
- data/ext/rbs_extension/lexer.re +147 -0
- data/ext/rbs_extension/lexstate.c +175 -0
- data/ext/rbs_extension/location.c +325 -0
- data/ext/rbs_extension/location.h +85 -0
- data/ext/rbs_extension/main.c +33 -0
- data/ext/rbs_extension/parser.c +2973 -0
- data/ext/rbs_extension/parser.h +18 -0
- data/ext/rbs_extension/parserstate.c +397 -0
- data/ext/rbs_extension/parserstate.h +163 -0
- data/ext/rbs_extension/rbs_extension.h +31 -0
- data/ext/rbs_extension/unescape.c +32 -0
- data/goodcheck.yml +91 -0
- data/include/rbs/constants.h +82 -0
- data/include/rbs/ruby_objs.h +72 -0
- data/include/rbs/util/rbs_constant_pool.h +219 -0
- data/include/rbs.h +7 -0
- data/lib/rbs/ancestor_graph.rb +92 -0
- data/lib/rbs/annotate/annotations.rb +199 -0
- data/lib/rbs/annotate/formatter.rb +92 -0
- data/lib/rbs/annotate/rdoc_annotator.rb +400 -0
- data/lib/rbs/annotate/rdoc_source.rb +131 -0
- data/lib/rbs/annotate.rb +8 -0
- data/lib/rbs/ast/annotation.rb +29 -0
- data/lib/rbs/ast/comment.rb +29 -0
- data/lib/rbs/ast/declarations.rb +467 -0
- data/lib/rbs/ast/directives.rb +49 -0
- data/lib/rbs/ast/members.rb +451 -0
- data/lib/rbs/ast/type_param.rb +225 -0
- data/lib/rbs/ast/visitor.rb +137 -0
- data/lib/rbs/buffer.rb +67 -0
- data/lib/rbs/builtin_names.rb +58 -0
- data/lib/rbs/cli/colored_io.rb +48 -0
- data/lib/rbs/cli/diff.rb +83 -0
- data/lib/rbs/cli/validate.rb +357 -0
- data/lib/rbs/cli.rb +1223 -0
- data/lib/rbs/collection/cleaner.rb +38 -0
- data/lib/rbs/collection/config/lockfile.rb +92 -0
- data/lib/rbs/collection/config/lockfile_generator.rb +218 -0
- data/lib/rbs/collection/config.rb +81 -0
- data/lib/rbs/collection/installer.rb +32 -0
- data/lib/rbs/collection/sources/base.rb +14 -0
- data/lib/rbs/collection/sources/git.rb +258 -0
- data/lib/rbs/collection/sources/local.rb +81 -0
- data/lib/rbs/collection/sources/rubygems.rb +48 -0
- data/lib/rbs/collection/sources/stdlib.rb +50 -0
- data/lib/rbs/collection/sources.rb +38 -0
- data/lib/rbs/collection.rb +16 -0
- data/lib/rbs/constant.rb +28 -0
- data/lib/rbs/definition.rb +401 -0
- data/lib/rbs/definition_builder/ancestor_builder.rb +620 -0
- data/lib/rbs/definition_builder/method_builder.rb +254 -0
- data/lib/rbs/definition_builder.rb +845 -0
- data/lib/rbs/diff.rb +125 -0
- data/lib/rbs/environment/use_map.rb +77 -0
- data/lib/rbs/environment.rb +829 -0
- data/lib/rbs/environment_loader.rb +173 -0
- data/lib/rbs/environment_walker.rb +155 -0
- data/lib/rbs/errors.rb +645 -0
- data/lib/rbs/factory.rb +18 -0
- data/lib/rbs/file_finder.rb +28 -0
- data/lib/rbs/location_aux.rb +138 -0
- data/lib/rbs/locator.rb +243 -0
- data/lib/rbs/method_type.rb +143 -0
- data/lib/rbs/namespace.rb +125 -0
- data/lib/rbs/parser/lex_result.rb +15 -0
- data/lib/rbs/parser/token.rb +23 -0
- data/lib/rbs/parser_aux.rb +114 -0
- data/lib/rbs/prototype/helpers.rb +140 -0
- data/lib/rbs/prototype/node_usage.rb +99 -0
- data/lib/rbs/prototype/rb.rb +840 -0
- data/lib/rbs/prototype/rbi.rb +641 -0
- data/lib/rbs/prototype/runtime/helpers.rb +59 -0
- data/lib/rbs/prototype/runtime/reflection.rb +19 -0
- data/lib/rbs/prototype/runtime/value_object_generator.rb +279 -0
- data/lib/rbs/prototype/runtime.rb +667 -0
- data/lib/rbs/repository.rb +127 -0
- data/lib/rbs/resolver/constant_resolver.rb +219 -0
- data/lib/rbs/resolver/type_name_resolver.rb +91 -0
- data/lib/rbs/sorter.rb +198 -0
- data/lib/rbs/substitution.rb +83 -0
- data/lib/rbs/subtractor.rb +201 -0
- data/lib/rbs/test/errors.rb +80 -0
- data/lib/rbs/test/guaranteed.rb +30 -0
- data/lib/rbs/test/hook.rb +212 -0
- data/lib/rbs/test/observer.rb +19 -0
- data/lib/rbs/test/setup.rb +84 -0
- data/lib/rbs/test/setup_helper.rb +50 -0
- data/lib/rbs/test/tester.rb +167 -0
- data/lib/rbs/test/type_check.rb +435 -0
- data/lib/rbs/test.rb +112 -0
- data/lib/rbs/type_alias_dependency.rb +100 -0
- data/lib/rbs/type_alias_regularity.rb +126 -0
- data/lib/rbs/type_name.rb +109 -0
- data/lib/rbs/types.rb +1596 -0
- data/lib/rbs/unit_test/convertibles.rb +176 -0
- data/lib/rbs/unit_test/spy.rb +138 -0
- data/lib/rbs/unit_test/type_assertions.rb +347 -0
- data/lib/rbs/unit_test/with_aliases.rb +143 -0
- data/lib/rbs/unit_test.rb +6 -0
- data/lib/rbs/validator.rb +186 -0
- data/lib/rbs/variance_calculator.rb +189 -0
- data/lib/rbs/vendorer.rb +71 -0
- data/lib/rbs/version.rb +5 -0
- data/lib/rbs/writer.rb +424 -0
- data/lib/rbs.rb +94 -0
- data/lib/rdoc/discover.rb +20 -0
- data/lib/rdoc_plugin/parser.rb +163 -0
- data/rbs-relaxed.gemspec +48 -0
- data/schema/annotation.json +14 -0
- data/schema/comment.json +26 -0
- data/schema/decls.json +326 -0
- data/schema/function.json +87 -0
- data/schema/location.json +56 -0
- data/schema/members.json +266 -0
- data/schema/methodType.json +50 -0
- data/schema/typeParam.json +36 -0
- data/schema/types.json +317 -0
- data/sig/ancestor_builder.rbs +163 -0
- data/sig/ancestor_graph.rbs +60 -0
- data/sig/annotate/annotations.rbs +102 -0
- data/sig/annotate/formatter.rbs +24 -0
- data/sig/annotate/rdoc_annotater.rbs +82 -0
- data/sig/annotate/rdoc_source.rbs +30 -0
- data/sig/annotation.rbs +27 -0
- data/sig/buffer.rbs +32 -0
- data/sig/builtin_names.rbs +44 -0
- data/sig/cli/colored_io.rbs +15 -0
- data/sig/cli/diff.rbs +21 -0
- data/sig/cli/validate.rbs +43 -0
- data/sig/cli.rbs +87 -0
- data/sig/collection/cleaner.rbs +13 -0
- data/sig/collection/config/lockfile.rbs +74 -0
- data/sig/collection/config/lockfile_generator.rbs +66 -0
- data/sig/collection/config.rbs +46 -0
- data/sig/collection/installer.rbs +17 -0
- data/sig/collection/sources.rbs +214 -0
- data/sig/collection.rbs +4 -0
- data/sig/comment.rbs +26 -0
- data/sig/constant.rbs +21 -0
- data/sig/declarations.rbs +267 -0
- data/sig/definition.rbs +173 -0
- data/sig/definition_builder.rbs +165 -0
- data/sig/diff.rbs +28 -0
- data/sig/directives.rbs +77 -0
- data/sig/environment.rbs +279 -0
- data/sig/environment_loader.rbs +111 -0
- data/sig/environment_walker.rbs +65 -0
- data/sig/errors.rbs +405 -0
- data/sig/factory.rbs +5 -0
- data/sig/file_finder.rbs +28 -0
- data/sig/location.rbs +110 -0
- data/sig/locator.rbs +58 -0
- data/sig/manifest.yaml +7 -0
- data/sig/members.rbs +258 -0
- data/sig/method_builder.rbs +84 -0
- data/sig/method_types.rbs +58 -0
- data/sig/namespace.rbs +146 -0
- data/sig/parser.rbs +100 -0
- data/sig/prototype/helpers.rbs +27 -0
- data/sig/prototype/node_usage.rbs +20 -0
- data/sig/prototype/rb.rbs +96 -0
- data/sig/prototype/rbi.rbs +75 -0
- data/sig/prototype/runtime.rbs +182 -0
- data/sig/rbs.rbs +21 -0
- data/sig/rdoc/rbs.rbs +67 -0
- data/sig/repository.rbs +85 -0
- data/sig/resolver/constant_resolver.rbs +92 -0
- data/sig/resolver/context.rbs +34 -0
- data/sig/resolver/type_name_resolver.rbs +35 -0
- data/sig/shims/bundler.rbs +38 -0
- data/sig/shims/enumerable.rbs +5 -0
- data/sig/shims/rubygems.rbs +19 -0
- data/sig/sorter.rbs +41 -0
- data/sig/substitution.rbs +48 -0
- data/sig/subtractor.rbs +37 -0
- data/sig/test/errors.rbs +52 -0
- data/sig/test/guranteed.rbs +9 -0
- data/sig/test/type_check.rbs +19 -0
- data/sig/test.rbs +82 -0
- data/sig/type_alias_dependency.rbs +53 -0
- data/sig/type_alias_regularity.rbs +98 -0
- data/sig/type_param.rbs +110 -0
- data/sig/typename.rbs +79 -0
- data/sig/types.rbs +579 -0
- data/sig/unit_test/convertibles.rbs +154 -0
- data/sig/unit_test/spy.rbs +30 -0
- data/sig/unit_test/type_assertions.rbs +196 -0
- data/sig/unit_test/with_aliases.rbs +136 -0
- data/sig/use_map.rbs +35 -0
- data/sig/util.rbs +9 -0
- data/sig/validator.rbs +63 -0
- data/sig/variance_calculator.rbs +87 -0
- data/sig/vendorer.rbs +51 -0
- data/sig/version.rbs +3 -0
- data/sig/visitor.rbs +47 -0
- data/sig/writer.rbs +127 -0
- data/src/constants.c +153 -0
- data/src/ruby_objs.c +795 -0
- data/src/util/rbs_constant_pool.c +342 -0
- data/stdlib/abbrev/0/abbrev.rbs +66 -0
- data/stdlib/abbrev/0/array.rbs +26 -0
- data/stdlib/base64/0/base64.rbs +355 -0
- data/stdlib/benchmark/0/benchmark.rbs +452 -0
- data/stdlib/bigdecimal/0/big_decimal.rbs +1629 -0
- data/stdlib/bigdecimal-math/0/big_math.rbs +119 -0
- data/stdlib/bigdecimal-math/0/manifest.yaml +2 -0
- data/stdlib/cgi/0/core.rbs +1285 -0
- data/stdlib/cgi/0/manifest.yaml +3 -0
- data/stdlib/coverage/0/coverage.rbs +263 -0
- data/stdlib/csv/0/csv.rbs +3776 -0
- data/stdlib/csv/0/manifest.yaml +3 -0
- data/stdlib/date/0/date.rbs +1585 -0
- data/stdlib/date/0/date_time.rbs +616 -0
- data/stdlib/date/0/time.rbs +26 -0
- data/stdlib/dbm/0/dbm.rbs +421 -0
- data/stdlib/delegate/0/delegator.rbs +184 -0
- data/stdlib/delegate/0/kernel.rbs +47 -0
- data/stdlib/delegate/0/simple_delegator.rbs +96 -0
- data/stdlib/did_you_mean/0/did_you_mean.rbs +343 -0
- data/stdlib/digest/0/digest.rbs +577 -0
- data/stdlib/erb/0/erb.rbs +532 -0
- data/stdlib/etc/0/etc.rbs +865 -0
- data/stdlib/fileutils/0/fileutils.rbs +1734 -0
- data/stdlib/find/0/find.rbs +49 -0
- data/stdlib/forwardable/0/forwardable.rbs +268 -0
- data/stdlib/io-console/0/io-console.rbs +414 -0
- data/stdlib/ipaddr/0/ipaddr.rbs +428 -0
- data/stdlib/json/0/json.rbs +1916 -0
- data/stdlib/kconv/0/kconv.rbs +166 -0
- data/stdlib/logger/0/formatter.rbs +45 -0
- data/stdlib/logger/0/log_device.rbs +100 -0
- data/stdlib/logger/0/logger.rbs +796 -0
- data/stdlib/logger/0/manifest.yaml +2 -0
- data/stdlib/logger/0/period.rbs +17 -0
- data/stdlib/logger/0/severity.rbs +34 -0
- data/stdlib/minitest/0/kernel.rbs +42 -0
- data/stdlib/minitest/0/minitest/abstract_reporter.rbs +52 -0
- data/stdlib/minitest/0/minitest/assertion.rbs +17 -0
- data/stdlib/minitest/0/minitest/assertions.rbs +590 -0
- data/stdlib/minitest/0/minitest/backtrace_filter.rbs +23 -0
- data/stdlib/minitest/0/minitest/bench_spec.rbs +102 -0
- data/stdlib/minitest/0/minitest/benchmark.rbs +259 -0
- data/stdlib/minitest/0/minitest/composite_reporter.rbs +25 -0
- data/stdlib/minitest/0/minitest/compress.rbs +13 -0
- data/stdlib/minitest/0/minitest/error_on_warning.rbs +3 -0
- data/stdlib/minitest/0/minitest/expectation.rbs +2 -0
- data/stdlib/minitest/0/minitest/expectations.rbs +21 -0
- data/stdlib/minitest/0/minitest/guard.rbs +64 -0
- data/stdlib/minitest/0/minitest/mock.rbs +64 -0
- data/stdlib/minitest/0/minitest/parallel/executor.rbs +46 -0
- data/stdlib/minitest/0/minitest/parallel/test/class_methods.rbs +5 -0
- data/stdlib/minitest/0/minitest/parallel/test.rbs +3 -0
- data/stdlib/minitest/0/minitest/parallel.rbs +2 -0
- data/stdlib/minitest/0/minitest/pride_io.rbs +62 -0
- data/stdlib/minitest/0/minitest/pride_lol.rbs +19 -0
- data/stdlib/minitest/0/minitest/progress_reporter.rbs +11 -0
- data/stdlib/minitest/0/minitest/reportable.rbs +53 -0
- data/stdlib/minitest/0/minitest/reporter.rbs +5 -0
- data/stdlib/minitest/0/minitest/result.rbs +28 -0
- data/stdlib/minitest/0/minitest/runnable.rbs +163 -0
- data/stdlib/minitest/0/minitest/skip.rbs +6 -0
- data/stdlib/minitest/0/minitest/spec/dsl/instance_methods.rbs +48 -0
- data/stdlib/minitest/0/minitest/spec/dsl.rbs +129 -0
- data/stdlib/minitest/0/minitest/spec.rbs +11 -0
- data/stdlib/minitest/0/minitest/statistics_reporter.rbs +81 -0
- data/stdlib/minitest/0/minitest/summary_reporter.rbs +18 -0
- data/stdlib/minitest/0/minitest/test/lifecycle_hooks.rbs +92 -0
- data/stdlib/minitest/0/minitest/test.rbs +69 -0
- data/stdlib/minitest/0/minitest/unexpected_error.rbs +12 -0
- data/stdlib/minitest/0/minitest/unexpected_warning.rbs +6 -0
- data/stdlib/minitest/0/minitest/unit/test_case.rbs +3 -0
- data/stdlib/minitest/0/minitest/unit.rbs +4 -0
- data/stdlib/minitest/0/minitest.rbs +115 -0
- data/stdlib/monitor/0/monitor.rbs +363 -0
- data/stdlib/mutex_m/0/mutex_m.rbs +104 -0
- data/stdlib/net-http/0/manifest.yaml +3 -0
- data/stdlib/net-http/0/net-http.rbs +5552 -0
- data/stdlib/net-protocol/0/manifest.yaml +2 -0
- data/stdlib/net-protocol/0/net-protocol.rbs +56 -0
- data/stdlib/net-smtp/0/manifest.yaml +2 -0
- data/stdlib/net-smtp/0/net-smtp.rbs +55 -0
- data/stdlib/nkf/0/nkf.rbs +402 -0
- data/stdlib/objspace/0/objspace.rbs +487 -0
- data/stdlib/observable/0/observable.rbs +217 -0
- data/stdlib/open-uri/0/manifest.yaml +4 -0
- data/stdlib/open-uri/0/open-uri.rbs +393 -0
- data/stdlib/open3/0/open3.rbs +147 -0
- data/stdlib/openssl/0/manifest.yaml +3 -0
- data/stdlib/openssl/0/openssl.rbs +12113 -0
- data/stdlib/optparse/0/optparse.rbs +1725 -0
- data/stdlib/pathname/0/pathname.rbs +1406 -0
- data/stdlib/pp/0/manifest.yaml +2 -0
- data/stdlib/pp/0/pp.rbs +300 -0
- data/stdlib/prettyprint/0/prettyprint.rbs +383 -0
- data/stdlib/pstore/0/pstore.rbs +603 -0
- data/stdlib/psych/0/core_ext.rbs +12 -0
- data/stdlib/psych/0/dbm.rbs +237 -0
- data/stdlib/psych/0/manifest.yaml +3 -0
- data/stdlib/psych/0/psych.rbs +402 -0
- data/stdlib/psych/0/store.rbs +59 -0
- data/stdlib/pty/0/pty.rbs +237 -0
- data/stdlib/rdoc/0/code_object.rbs +51 -0
- data/stdlib/rdoc/0/comment.rbs +59 -0
- data/stdlib/rdoc/0/context.rbs +153 -0
- data/stdlib/rdoc/0/markup.rbs +117 -0
- data/stdlib/rdoc/0/parser.rbs +56 -0
- data/stdlib/rdoc/0/rdoc.rbs +391 -0
- data/stdlib/rdoc/0/ri.rbs +17 -0
- data/stdlib/rdoc/0/store.rbs +48 -0
- data/stdlib/rdoc/0/top_level.rbs +97 -0
- data/stdlib/resolv/0/manifest.yaml +3 -0
- data/stdlib/resolv/0/resolv.rbs +1830 -0
- data/stdlib/ripper/0/ripper.rbs +1648 -0
- data/stdlib/securerandom/0/securerandom.rbs +62 -0
- data/stdlib/shellwords/0/shellwords.rbs +229 -0
- data/stdlib/singleton/0/singleton.rbs +131 -0
- data/stdlib/socket/0/addrinfo.rbs +666 -0
- data/stdlib/socket/0/basic_socket.rbs +590 -0
- data/stdlib/socket/0/constants.rbs +2295 -0
- data/stdlib/socket/0/ip_socket.rbs +92 -0
- data/stdlib/socket/0/socket.rbs +4157 -0
- data/stdlib/socket/0/socket_error.rbs +5 -0
- data/stdlib/socket/0/tcp_server.rbs +192 -0
- data/stdlib/socket/0/tcp_socket.rbs +79 -0
- data/stdlib/socket/0/udp_socket.rbs +133 -0
- data/stdlib/socket/0/unix_server.rbs +169 -0
- data/stdlib/socket/0/unix_socket.rbs +172 -0
- data/stdlib/stringio/0/stringio.rbs +567 -0
- data/stdlib/strscan/0/string_scanner.rbs +1627 -0
- data/stdlib/tempfile/0/tempfile.rbs +479 -0
- data/stdlib/time/0/time.rbs +432 -0
- data/stdlib/timeout/0/timeout.rbs +81 -0
- data/stdlib/tmpdir/0/tmpdir.rbs +69 -0
- data/stdlib/tsort/0/cyclic.rbs +5 -0
- data/stdlib/tsort/0/interfaces.rbs +20 -0
- data/stdlib/tsort/0/tsort.rbs +409 -0
- data/stdlib/uri/0/common.rbs +582 -0
- data/stdlib/uri/0/file.rbs +118 -0
- data/stdlib/uri/0/ftp.rbs +13 -0
- data/stdlib/uri/0/generic.rbs +1108 -0
- data/stdlib/uri/0/http.rbs +104 -0
- data/stdlib/uri/0/https.rbs +14 -0
- data/stdlib/uri/0/ldap.rbs +230 -0
- data/stdlib/uri/0/ldaps.rbs +14 -0
- data/stdlib/uri/0/mailto.rbs +92 -0
- data/stdlib/uri/0/rfc2396_parser.rbs +189 -0
- data/stdlib/uri/0/rfc3986_parser.rbs +2 -0
- data/stdlib/uri/0/ws.rbs +13 -0
- data/stdlib/uri/0/wss.rbs +9 -0
- data/stdlib/yaml/0/manifest.yaml +2 -0
- data/stdlib/yaml/0/yaml.rbs +1 -0
- data/stdlib/zlib/0/buf_error.rbs +10 -0
- data/stdlib/zlib/0/data_error.rbs +10 -0
- data/stdlib/zlib/0/deflate.rbs +210 -0
- data/stdlib/zlib/0/error.rbs +20 -0
- data/stdlib/zlib/0/gzip_file/crc_error.rbs +12 -0
- data/stdlib/zlib/0/gzip_file/error.rbs +23 -0
- data/stdlib/zlib/0/gzip_file/length_error.rbs +12 -0
- data/stdlib/zlib/0/gzip_file/no_footer.rbs +11 -0
- data/stdlib/zlib/0/gzip_file.rbs +156 -0
- data/stdlib/zlib/0/gzip_reader.rbs +293 -0
- data/stdlib/zlib/0/gzip_writer.rbs +166 -0
- data/stdlib/zlib/0/inflate.rbs +180 -0
- data/stdlib/zlib/0/mem_error.rbs +10 -0
- data/stdlib/zlib/0/need_dict.rbs +13 -0
- data/stdlib/zlib/0/stream_end.rbs +11 -0
- data/stdlib/zlib/0/stream_error.rbs +11 -0
- data/stdlib/zlib/0/version_error.rbs +11 -0
- data/stdlib/zlib/0/zlib.rbs +449 -0
- data/stdlib/zlib/0/zstream.rbs +200 -0
- metadata +532 -0
data/core/enumerable.rbs
ADDED
@@ -0,0 +1,2405 @@
|
|
1
|
+
# <!-- rdoc-file=enum.c -->
|
2
|
+
# ## What's Here
|
3
|
+
#
|
4
|
+
# Module Enumerable provides methods that are useful to a collection class for:
|
5
|
+
#
|
6
|
+
# * [Querying](rdoc-ref:Enumerable@Methods+for+Querying)
|
7
|
+
# * [Fetching](rdoc-ref:Enumerable@Methods+for+Fetching)
|
8
|
+
# * [Searching and
|
9
|
+
# Filtering](rdoc-ref:Enumerable@Methods+for+Searching+and+Filtering)
|
10
|
+
# * [Sorting](rdoc-ref:Enumerable@Methods+for+Sorting)
|
11
|
+
# * [Iterating](rdoc-ref:Enumerable@Methods+for+Iterating)
|
12
|
+
# * [And more....](rdoc-ref:Enumerable@Other+Methods)
|
13
|
+
#
|
14
|
+
# ### Methods for Querying
|
15
|
+
#
|
16
|
+
# These methods return information about the Enumerable other than the elements
|
17
|
+
# themselves:
|
18
|
+
#
|
19
|
+
# * #member? (aliased as #include?): Returns `true` if `self == object`,
|
20
|
+
# `false` otherwise.
|
21
|
+
# * #all?: Returns `true` if all elements meet a specified criterion; `false`
|
22
|
+
# otherwise.
|
23
|
+
# * #any?: Returns `true` if any element meets a specified criterion; `false`
|
24
|
+
# otherwise.
|
25
|
+
# * #none?: Returns `true` if no element meets a specified criterion; `false`
|
26
|
+
# otherwise.
|
27
|
+
# * #one?: Returns `true` if exactly one element meets a specified criterion;
|
28
|
+
# `false` otherwise.
|
29
|
+
# * #count: Returns the count of elements, based on an argument or block
|
30
|
+
# criterion, if given.
|
31
|
+
# * #tally: Returns a new Hash containing the counts of occurrences of each
|
32
|
+
# element.
|
33
|
+
#
|
34
|
+
# ### Methods for Fetching
|
35
|
+
#
|
36
|
+
# These methods return entries from the Enumerable, without modifying it:
|
37
|
+
#
|
38
|
+
# *Leading, trailing, or all elements*:
|
39
|
+
#
|
40
|
+
# * #to_a (aliased as #entries): Returns all elements.
|
41
|
+
# * #first: Returns the first element or leading elements.
|
42
|
+
# * #take: Returns a specified number of leading elements.
|
43
|
+
# * #drop: Returns a specified number of trailing elements.
|
44
|
+
# * #take_while: Returns leading elements as specified by the given block.
|
45
|
+
# * #drop_while: Returns trailing elements as specified by the given block.
|
46
|
+
#
|
47
|
+
# *Minimum and maximum value elements*:
|
48
|
+
#
|
49
|
+
# * #min: Returns the elements whose values are smallest among the elements,
|
50
|
+
# as determined by `#<=>` or a given block.
|
51
|
+
# * #max: Returns the elements whose values are largest among the elements, as
|
52
|
+
# determined by `#<=>` or a given block.
|
53
|
+
# * #minmax: Returns a 2-element Array containing the smallest and largest
|
54
|
+
# elements.
|
55
|
+
# * #min_by: Returns the smallest element, as determined by the given block.
|
56
|
+
# * #max_by: Returns the largest element, as determined by the given block.
|
57
|
+
# * #minmax_by: Returns the smallest and largest elements, as determined by
|
58
|
+
# the given block.
|
59
|
+
#
|
60
|
+
# *Groups, slices, and partitions*:
|
61
|
+
#
|
62
|
+
# * #group_by: Returns a Hash that partitions the elements into groups.
|
63
|
+
# * #partition: Returns elements partitioned into two new Arrays, as
|
64
|
+
# determined by the given block.
|
65
|
+
# * #slice_after: Returns a new Enumerator whose entries are a partition of
|
66
|
+
# `self`, based either on a given `object` or a given block.
|
67
|
+
# * #slice_before: Returns a new Enumerator whose entries are a partition of
|
68
|
+
# `self`, based either on a given `object` or a given block.
|
69
|
+
# * #slice_when: Returns a new Enumerator whose entries are a partition of
|
70
|
+
# `self` based on the given block.
|
71
|
+
# * #chunk: Returns elements organized into chunks as specified by the given
|
72
|
+
# block.
|
73
|
+
# * #chunk_while: Returns elements organized into chunks as specified by the
|
74
|
+
# given block.
|
75
|
+
#
|
76
|
+
# ### Methods for Searching and Filtering
|
77
|
+
#
|
78
|
+
# These methods return elements that meet a specified criterion:
|
79
|
+
#
|
80
|
+
# * #find (aliased as #detect): Returns an element selected by the block.
|
81
|
+
# * #find_all (aliased as #filter, #select): Returns elements selected by the
|
82
|
+
# block.
|
83
|
+
# * #find_index: Returns the index of an element selected by a given object or
|
84
|
+
# block.
|
85
|
+
# * #reject: Returns elements not rejected by the block.
|
86
|
+
# * #uniq: Returns elements that are not duplicates.
|
87
|
+
#
|
88
|
+
# ### Methods for Sorting
|
89
|
+
#
|
90
|
+
# These methods return elements in sorted order:
|
91
|
+
#
|
92
|
+
# * #sort: Returns the elements, sorted by `#<=>` or the given block.
|
93
|
+
# * #sort_by: Returns the elements, sorted by the given block.
|
94
|
+
#
|
95
|
+
# ### Methods for Iterating
|
96
|
+
#
|
97
|
+
# * #each_entry: Calls the block with each successive element (slightly
|
98
|
+
# different from #each).
|
99
|
+
# * #each_with_index: Calls the block with each successive element and its
|
100
|
+
# index.
|
101
|
+
# * #each_with_object: Calls the block with each successive element and a
|
102
|
+
# given object.
|
103
|
+
# * #each_slice: Calls the block with successive non-overlapping slices.
|
104
|
+
# * #each_cons: Calls the block with successive overlapping slices. (different
|
105
|
+
# from #each_slice).
|
106
|
+
# * #reverse_each: Calls the block with each successive element, in reverse
|
107
|
+
# order.
|
108
|
+
#
|
109
|
+
# ### Other Methods
|
110
|
+
#
|
111
|
+
# * #collect (aliased as #map): Returns objects returned by the block.
|
112
|
+
# * #filter_map: Returns truthy objects returned by the block.
|
113
|
+
# * #flat_map (aliased as #collect_concat): Returns flattened objects returned
|
114
|
+
# by the block.
|
115
|
+
# * #grep: Returns elements selected by a given object or objects returned by
|
116
|
+
# a given block.
|
117
|
+
# * #grep_v: Returns elements selected by a given object or objects returned
|
118
|
+
# by a given block.
|
119
|
+
# * #inject (aliased as #reduce): Returns the object formed by combining all
|
120
|
+
# elements.
|
121
|
+
# * #sum: Returns the sum of the elements, using method `+`.
|
122
|
+
# * #zip: Combines each element with elements from other enumerables; returns
|
123
|
+
# the n-tuples or calls the block with each.
|
124
|
+
# * #cycle: Calls the block with each element, cycling repeatedly.
|
125
|
+
#
|
126
|
+
# ## Usage
|
127
|
+
#
|
128
|
+
# To use module Enumerable in a collection class:
|
129
|
+
#
|
130
|
+
# * Include it:
|
131
|
+
#
|
132
|
+
# include Enumerable
|
133
|
+
#
|
134
|
+
# * Implement method `#each` which must yield successive elements of the
|
135
|
+
# collection. The method will be called by almost any Enumerable method.
|
136
|
+
#
|
137
|
+
# Example:
|
138
|
+
#
|
139
|
+
# class Foo
|
140
|
+
# include Enumerable
|
141
|
+
# def each
|
142
|
+
# yield 1
|
143
|
+
# yield 1, 2
|
144
|
+
# yield
|
145
|
+
# end
|
146
|
+
# end
|
147
|
+
# Foo.new.each_entry{ |element| p element }
|
148
|
+
#
|
149
|
+
# Output:
|
150
|
+
#
|
151
|
+
# 1
|
152
|
+
# [1, 2]
|
153
|
+
# nil
|
154
|
+
#
|
155
|
+
# ## Enumerable in Ruby Classes
|
156
|
+
#
|
157
|
+
# These Ruby core classes include (or extend) Enumerable:
|
158
|
+
#
|
159
|
+
# * ARGF
|
160
|
+
# * Array
|
161
|
+
# * Dir
|
162
|
+
# * Enumerator
|
163
|
+
# * ENV (extends)
|
164
|
+
# * Hash
|
165
|
+
# * IO
|
166
|
+
# * Range
|
167
|
+
# * Struct
|
168
|
+
#
|
169
|
+
# These Ruby standard library classes include Enumerable:
|
170
|
+
#
|
171
|
+
# * CSV
|
172
|
+
# * CSV::Table
|
173
|
+
# * CSV::Row
|
174
|
+
# * Set
|
175
|
+
#
|
176
|
+
# Virtually all methods in Enumerable call method `#each` in the including
|
177
|
+
# class:
|
178
|
+
#
|
179
|
+
# * `Hash#each` yields the next key-value pair as a 2-element Array.
|
180
|
+
# * `Struct#each` yields the next name-value pair as a 2-element Array.
|
181
|
+
# * For the other classes above, `#each` yields the next object from the
|
182
|
+
# collection.
|
183
|
+
#
|
184
|
+
# ## About the Examples
|
185
|
+
#
|
186
|
+
# The example code snippets for the Enumerable methods:
|
187
|
+
#
|
188
|
+
# * Always show the use of one or more Array-like classes (often Array
|
189
|
+
# itself).
|
190
|
+
# * Sometimes show the use of a Hash-like class. For some methods, though, the
|
191
|
+
# usage would not make sense, and so it is not shown. Example: #tally would
|
192
|
+
# find exactly one of each Hash entry.
|
193
|
+
#
|
194
|
+
module Enumerable[unchecked out Elem] : _Each[Elem]
|
195
|
+
# <!--
|
196
|
+
# rdoc-file=enum.c
|
197
|
+
# - all? -> true or false
|
198
|
+
# - all?(pattern) -> true or false
|
199
|
+
# - all? {|element| ... } -> true or false
|
200
|
+
# -->
|
201
|
+
# Returns whether every element meets a given criterion.
|
202
|
+
#
|
203
|
+
# If `self` has no element, returns `true` and argument or block are not used.
|
204
|
+
#
|
205
|
+
# With no argument and no block, returns whether every element is truthy:
|
206
|
+
#
|
207
|
+
# (1..4).all? # => true
|
208
|
+
# %w[a b c d].all? # => true
|
209
|
+
# [1, 2, nil].all? # => false
|
210
|
+
# ['a','b', false].all? # => false
|
211
|
+
# [].all? # => true
|
212
|
+
#
|
213
|
+
# With argument `pattern` and no block, returns whether for each element
|
214
|
+
# `element`, `pattern === element`:
|
215
|
+
#
|
216
|
+
# (1..4).all?(Integer) # => true
|
217
|
+
# (1..4).all?(Numeric) # => true
|
218
|
+
# (1..4).all?(Float) # => false
|
219
|
+
# %w[bar baz bat bam].all?(/ba/) # => true
|
220
|
+
# %w[bar baz bat bam].all?(/bar/) # => false
|
221
|
+
# %w[bar baz bat bam].all?('ba') # => false
|
222
|
+
# {foo: 0, bar: 1, baz: 2}.all?(Array) # => true
|
223
|
+
# {foo: 0, bar: 1, baz: 2}.all?(Hash) # => false
|
224
|
+
# [].all?(Integer) # => true
|
225
|
+
#
|
226
|
+
# With a block given, returns whether the block returns a truthy value for every
|
227
|
+
# element:
|
228
|
+
#
|
229
|
+
# (1..4).all? {|element| element < 5 } # => true
|
230
|
+
# (1..4).all? {|element| element < 4 } # => false
|
231
|
+
# {foo: 0, bar: 1, baz: 2}.all? {|key, value| value < 3 } # => true
|
232
|
+
# {foo: 0, bar: 1, baz: 2}.all? {|key, value| value < 2 } # => false
|
233
|
+
#
|
234
|
+
# Related: #any?, #none? #one?.
|
235
|
+
#
|
236
|
+
def all?: () -> bool
|
237
|
+
| () { (Elem) -> boolish } -> bool
|
238
|
+
|
239
|
+
# <!--
|
240
|
+
# rdoc-file=enum.c
|
241
|
+
# - any? -> true or false
|
242
|
+
# - any?(pattern) -> true or false
|
243
|
+
# - any? {|element| ... } -> true or false
|
244
|
+
# -->
|
245
|
+
# Returns whether any element meets a given criterion.
|
246
|
+
#
|
247
|
+
# If `self` has no element, returns `false` and argument or block are not used.
|
248
|
+
#
|
249
|
+
# With no argument and no block, returns whether any element is truthy:
|
250
|
+
#
|
251
|
+
# (1..4).any? # => true
|
252
|
+
# %w[a b c d].any? # => true
|
253
|
+
# [1, false, nil].any? # => true
|
254
|
+
# [].any? # => false
|
255
|
+
#
|
256
|
+
# With argument `pattern` and no block, returns whether for any element
|
257
|
+
# `element`, `pattern === element`:
|
258
|
+
#
|
259
|
+
# [nil, false, 0].any?(Integer) # => true
|
260
|
+
# [nil, false, 0].any?(Numeric) # => true
|
261
|
+
# [nil, false, 0].any?(Float) # => false
|
262
|
+
# %w[bar baz bat bam].any?(/m/) # => true
|
263
|
+
# %w[bar baz bat bam].any?(/foo/) # => false
|
264
|
+
# %w[bar baz bat bam].any?('ba') # => false
|
265
|
+
# {foo: 0, bar: 1, baz: 2}.any?(Array) # => true
|
266
|
+
# {foo: 0, bar: 1, baz: 2}.any?(Hash) # => false
|
267
|
+
# [].any?(Integer) # => false
|
268
|
+
#
|
269
|
+
# With a block given, returns whether the block returns a truthy value for any
|
270
|
+
# element:
|
271
|
+
#
|
272
|
+
# (1..4).any? {|element| element < 2 } # => true
|
273
|
+
# (1..4).any? {|element| element < 1 } # => false
|
274
|
+
# {foo: 0, bar: 1, baz: 2}.any? {|key, value| value < 1 } # => true
|
275
|
+
# {foo: 0, bar: 1, baz: 2}.any? {|key, value| value < 0 } # => false
|
276
|
+
#
|
277
|
+
# Related: #all?, #none?, #one?.
|
278
|
+
#
|
279
|
+
def any?: () -> bool
|
280
|
+
| () { (Elem) -> boolish } -> bool
|
281
|
+
|
282
|
+
# <!--
|
283
|
+
# rdoc-file=enum.c
|
284
|
+
# - map {|element| ... } -> array
|
285
|
+
# - map -> enumerator
|
286
|
+
# -->
|
287
|
+
# Returns an array of objects returned by the block.
|
288
|
+
#
|
289
|
+
# With a block given, calls the block with successive elements; returns an array
|
290
|
+
# of the objects returned by the block:
|
291
|
+
#
|
292
|
+
# (0..4).map {|i| i*i } # => [0, 1, 4, 9, 16]
|
293
|
+
# {foo: 0, bar: 1, baz: 2}.map {|key, value| value*2} # => [0, 2, 4]
|
294
|
+
#
|
295
|
+
# With no block given, returns an Enumerator.
|
296
|
+
#
|
297
|
+
def collect: [U] () { (Elem arg0) -> U } -> ::Array[U]
|
298
|
+
| () -> ::Enumerator[Elem, ::Array[untyped]]
|
299
|
+
|
300
|
+
# <!-- rdoc-file=enum.c -->
|
301
|
+
# Returns an array of flattened objects returned by the block.
|
302
|
+
#
|
303
|
+
# With a block given, calls the block with successive elements; returns a
|
304
|
+
# flattened array of objects returned by the block:
|
305
|
+
#
|
306
|
+
# [0, 1, 2, 3].flat_map {|element| -element } # => [0, -1, -2, -3]
|
307
|
+
# [0, 1, 2, 3].flat_map {|element| [element, -element] } # => [0, 0, 1, -1, 2, -2, 3, -3]
|
308
|
+
# [[0, 1], [2, 3]].flat_map {|e| e + [100] } # => [0, 1, 100, 2, 3, 100]
|
309
|
+
# {foo: 0, bar: 1, baz: 2}.flat_map {|key, value| [key, value] } # => [:foo, 0, :bar, 1, :baz, 2]
|
310
|
+
#
|
311
|
+
# With no block given, returns an Enumerator.
|
312
|
+
#
|
313
|
+
# Alias: #collect_concat.
|
314
|
+
#
|
315
|
+
def collect_concat: [U] () { (Elem) -> (::Array[U] | U) } -> ::Array[U]
|
316
|
+
| () -> ::Enumerator[Elem, ::Array[untyped]]
|
317
|
+
|
318
|
+
# <!--
|
319
|
+
# rdoc-file=enum.c
|
320
|
+
# - compact -> array
|
321
|
+
# -->
|
322
|
+
# Returns an array of all non-`nil` elements:
|
323
|
+
#
|
324
|
+
# a = [nil, 0, nil, 'a', false, nil, false, nil, 'a', nil, 0, nil]
|
325
|
+
# a.compact # => [0, "a", false, false, "a", 0]
|
326
|
+
#
|
327
|
+
def compact: () -> Array[Elem]
|
328
|
+
|
329
|
+
# <!--
|
330
|
+
# rdoc-file=enum.c
|
331
|
+
# - count -> integer
|
332
|
+
# - count(object) -> integer
|
333
|
+
# - count {|element| ... } -> integer
|
334
|
+
# -->
|
335
|
+
# Returns the count of elements, based on an argument or block criterion, if
|
336
|
+
# given.
|
337
|
+
#
|
338
|
+
# With no argument and no block given, returns the number of elements:
|
339
|
+
#
|
340
|
+
# [0, 1, 2].count # => 3
|
341
|
+
# {foo: 0, bar: 1, baz: 2}.count # => 3
|
342
|
+
#
|
343
|
+
# With argument `object` given, returns the number of elements that are `==` to
|
344
|
+
# `object`:
|
345
|
+
#
|
346
|
+
# [0, 1, 2, 1].count(1) # => 2
|
347
|
+
#
|
348
|
+
# With a block given, calls the block with each element and returns the number
|
349
|
+
# of elements for which the block returns a truthy value:
|
350
|
+
#
|
351
|
+
# [0, 1, 2, 3].count {|element| element < 2} # => 2
|
352
|
+
# {foo: 0, bar: 1, baz: 2}.count {|key, value| value < 2} # => 2
|
353
|
+
#
|
354
|
+
def count: () -> Integer
|
355
|
+
| (Elem) -> Integer
|
356
|
+
| () { (Elem) -> boolish } -> Integer
|
357
|
+
|
358
|
+
# <!--
|
359
|
+
# rdoc-file=enum.c
|
360
|
+
# - cycle(n = nil) {|element| ...} -> nil
|
361
|
+
# - cycle(n = nil) -> enumerator
|
362
|
+
# -->
|
363
|
+
# When called with positive integer argument `n` and a block, calls the block
|
364
|
+
# with each element, then does so again, until it has done so `n` times; returns
|
365
|
+
# `nil`:
|
366
|
+
#
|
367
|
+
# a = []
|
368
|
+
# (1..4).cycle(3) {|element| a.push(element) } # => nil
|
369
|
+
# a # => [1, 2, 3, 4, 1, 2, 3, 4, 1, 2, 3, 4]
|
370
|
+
# a = []
|
371
|
+
# ('a'..'d').cycle(2) {|element| a.push(element) }
|
372
|
+
# a # => ["a", "b", "c", "d", "a", "b", "c", "d"]
|
373
|
+
# a = []
|
374
|
+
# {foo: 0, bar: 1, baz: 2}.cycle(2) {|element| a.push(element) }
|
375
|
+
# a # => [[:foo, 0], [:bar, 1], [:baz, 2], [:foo, 0], [:bar, 1], [:baz, 2]]
|
376
|
+
#
|
377
|
+
# If count is zero or negative, does not call the block.
|
378
|
+
#
|
379
|
+
# When called with a block and `n` is `nil`, cycles forever.
|
380
|
+
#
|
381
|
+
# When no block is given, returns an Enumerator.
|
382
|
+
#
|
383
|
+
def cycle: (?Integer n) { (Elem arg0) -> untyped } -> NilClass
|
384
|
+
| (?Integer n) -> ::Enumerator[Elem, NilClass]
|
385
|
+
|
386
|
+
# <!-- rdoc-file=enum.c -->
|
387
|
+
# Returns the first element for which the block returns a truthy value.
|
388
|
+
#
|
389
|
+
# With a block given, calls the block with successive elements of the
|
390
|
+
# collection; returns the first element for which the block returns a truthy
|
391
|
+
# value:
|
392
|
+
#
|
393
|
+
# (0..9).find {|element| element > 2} # => 3
|
394
|
+
#
|
395
|
+
# If no such element is found, calls `if_none_proc` and returns its return
|
396
|
+
# value.
|
397
|
+
#
|
398
|
+
# (0..9).find(proc {false}) {|element| element > 12} # => false
|
399
|
+
# {foo: 0, bar: 1, baz: 2}.find {|key, value| key.start_with?('b') } # => [:bar, 1]
|
400
|
+
# {foo: 0, bar: 1, baz: 2}.find(proc {[]}) {|key, value| key.start_with?('c') } # => []
|
401
|
+
#
|
402
|
+
# With no block given, returns an Enumerator.
|
403
|
+
#
|
404
|
+
def detect: (?Proc ifnone) { (Elem) -> boolish } -> Elem?
|
405
|
+
| (?Proc ifnone) -> ::Enumerator[Elem, Elem?]
|
406
|
+
|
407
|
+
# <!--
|
408
|
+
# rdoc-file=enum.c
|
409
|
+
# - drop(n) -> array
|
410
|
+
# -->
|
411
|
+
# For positive integer `n`, returns an array containing all but the first `n`
|
412
|
+
# elements:
|
413
|
+
#
|
414
|
+
# r = (1..4)
|
415
|
+
# r.drop(3) # => [4]
|
416
|
+
# r.drop(2) # => [3, 4]
|
417
|
+
# r.drop(1) # => [2, 3, 4]
|
418
|
+
# r.drop(0) # => [1, 2, 3, 4]
|
419
|
+
# r.drop(50) # => []
|
420
|
+
#
|
421
|
+
# h = {foo: 0, bar: 1, baz: 2, bat: 3}
|
422
|
+
# h.drop(2) # => [[:baz, 2], [:bat, 3]]
|
423
|
+
#
|
424
|
+
def drop: (Integer n) -> ::Array[Elem]
|
425
|
+
|
426
|
+
# <!--
|
427
|
+
# rdoc-file=enum.c
|
428
|
+
# - drop_while {|element| ... } -> array
|
429
|
+
# - drop_while -> enumerator
|
430
|
+
# -->
|
431
|
+
# Calls the block with successive elements as long as the block returns a truthy
|
432
|
+
# value; returns an array of all elements after that point:
|
433
|
+
#
|
434
|
+
# (1..4).drop_while{|i| i < 3 } # => [3, 4]
|
435
|
+
# h = {foo: 0, bar: 1, baz: 2}
|
436
|
+
# a = h.drop_while{|element| key, value = *element; value < 2 }
|
437
|
+
# a # => [[:baz, 2]]
|
438
|
+
#
|
439
|
+
# With no block given, returns an Enumerator.
|
440
|
+
#
|
441
|
+
def drop_while: () { (Elem) -> boolish } -> ::Array[Elem]
|
442
|
+
| () -> ::Enumerator[Elem, ::Array[Elem]]
|
443
|
+
|
444
|
+
# <!--
|
445
|
+
# rdoc-file=enum.c
|
446
|
+
# - each_cons(n) { ... } -> self
|
447
|
+
# - each_cons(n) -> enumerator
|
448
|
+
# -->
|
449
|
+
# Calls the block with each successive overlapped `n`-tuple of elements; returns
|
450
|
+
# `self`:
|
451
|
+
#
|
452
|
+
# a = []
|
453
|
+
# (1..5).each_cons(3) {|element| a.push(element) }
|
454
|
+
# a # => [[1, 2, 3], [2, 3, 4], [3, 4, 5]]
|
455
|
+
#
|
456
|
+
# a = []
|
457
|
+
# h = {foo: 0, bar: 1, baz: 2, bam: 3}
|
458
|
+
# h.each_cons(2) {|element| a.push(element) }
|
459
|
+
# a # => [[[:foo, 0], [:bar, 1]], [[:bar, 1], [:baz, 2]], [[:baz, 2], [:bam, 3]]]
|
460
|
+
#
|
461
|
+
# With no block given, returns an Enumerator.
|
462
|
+
#
|
463
|
+
def each_cons: (Integer n) { (::Array[Elem]) -> void } -> self
|
464
|
+
| (Integer n) -> ::Enumerator[::Array[Elem], self]
|
465
|
+
|
466
|
+
# <!--
|
467
|
+
# rdoc-file=enum.c
|
468
|
+
# - each_with_index(*args) {|element, i| ..... } -> self
|
469
|
+
# - each_with_index(*args) -> enumerator
|
470
|
+
# -->
|
471
|
+
# Invoke `self.each` with `*args`. With a block given, the block receives each
|
472
|
+
# element and its index; returns `self`:
|
473
|
+
#
|
474
|
+
# h = {}
|
475
|
+
# (1..4).each_with_index {|element, i| h[element] = i } # => 1..4
|
476
|
+
# h # => {1=>0, 2=>1, 3=>2, 4=>3}
|
477
|
+
#
|
478
|
+
# h = {}
|
479
|
+
# %w[a b c d].each_with_index {|element, i| h[element] = i }
|
480
|
+
# # => ["a", "b", "c", "d"]
|
481
|
+
# h # => {"a"=>0, "b"=>1, "c"=>2, "d"=>3}
|
482
|
+
#
|
483
|
+
# a = []
|
484
|
+
# h = {foo: 0, bar: 1, baz: 2}
|
485
|
+
# h.each_with_index {|element, i| a.push([i, element]) }
|
486
|
+
# # => {:foo=>0, :bar=>1, :baz=>2}
|
487
|
+
# a # => [[0, [:foo, 0]], [1, [:bar, 1]], [2, [:baz, 2]]]
|
488
|
+
#
|
489
|
+
# With no block given, returns an Enumerator.
|
490
|
+
#
|
491
|
+
def each_with_index: () { (Elem, Integer index) -> untyped } -> self
|
492
|
+
| () -> ::Enumerator[[ Elem, Integer ], self]
|
493
|
+
|
494
|
+
# <!--
|
495
|
+
# rdoc-file=enum.c
|
496
|
+
# - each_with_object(object) { |(*args), memo_object| ... } -> object
|
497
|
+
# - each_with_object(object) -> enumerator
|
498
|
+
# -->
|
499
|
+
# Calls the block once for each element, passing both the element and the given
|
500
|
+
# object:
|
501
|
+
#
|
502
|
+
# (1..4).each_with_object([]) {|i, a| a.push(i**2) }
|
503
|
+
# # => [1, 4, 9, 16]
|
504
|
+
#
|
505
|
+
# {foo: 0, bar: 1, baz: 2}.each_with_object({}) {|(k, v), h| h[v] = k }
|
506
|
+
# # => {0=>:foo, 1=>:bar, 2=>:baz}
|
507
|
+
#
|
508
|
+
# With no block given, returns an Enumerator.
|
509
|
+
#
|
510
|
+
def each_with_object: [U] (U obj) { (Elem, U obj) -> untyped } -> U
|
511
|
+
| [U] (U obj) -> ::Enumerator[[ Elem, U ], U]
|
512
|
+
|
513
|
+
# <!-- rdoc-file=enum.c -->
|
514
|
+
# Returns an array containing the items in `self`:
|
515
|
+
#
|
516
|
+
# (0..4).to_a # => [0, 1, 2, 3, 4]
|
517
|
+
#
|
518
|
+
def entries: () -> ::Array[Elem]
|
519
|
+
|
520
|
+
def enum_for: (Symbol method, *untyped, **untyped) ?{ (?) -> Integer } -> Enumerator[untyped, untyped]
|
521
|
+
| () ?{ () -> Integer } -> Enumerator[Elem, self]
|
522
|
+
|
523
|
+
%a{annotate:rdoc:skip}
|
524
|
+
alias to_enum enum_for
|
525
|
+
|
526
|
+
# <!--
|
527
|
+
# rdoc-file=enum.c
|
528
|
+
# - select {|element| ... } -> array
|
529
|
+
# - select -> enumerator
|
530
|
+
# -->
|
531
|
+
# Returns an array containing elements selected by the block.
|
532
|
+
#
|
533
|
+
# With a block given, calls the block with successive elements; returns an array
|
534
|
+
# of those elements for which the block returns a truthy value:
|
535
|
+
#
|
536
|
+
# (0..9).select {|element| element % 3 == 0 } # => [0, 3, 6, 9]
|
537
|
+
# a = {foo: 0, bar: 1, baz: 2}.select {|key, value| key.start_with?('b') }
|
538
|
+
# a # => {:bar=>1, :baz=>2}
|
539
|
+
#
|
540
|
+
# With no block given, returns an Enumerator.
|
541
|
+
#
|
542
|
+
# Related: #reject.
|
543
|
+
#
|
544
|
+
def find_all: () { (Elem) -> boolish } -> ::Array[Elem]
|
545
|
+
| () -> ::Enumerator[Elem, ::Array[Elem]]
|
546
|
+
|
547
|
+
# <!-- rdoc-file=enum.c -->
|
548
|
+
# Returns an array containing elements selected by the block.
|
549
|
+
#
|
550
|
+
# With a block given, calls the block with successive elements; returns an array
|
551
|
+
# of those elements for which the block returns a truthy value:
|
552
|
+
#
|
553
|
+
# (0..9).select {|element| element % 3 == 0 } # => [0, 3, 6, 9]
|
554
|
+
# a = {foo: 0, bar: 1, baz: 2}.select {|key, value| key.start_with?('b') }
|
555
|
+
# a # => {:bar=>1, :baz=>2}
|
556
|
+
#
|
557
|
+
# With no block given, returns an Enumerator.
|
558
|
+
#
|
559
|
+
# Related: #reject.
|
560
|
+
#
|
561
|
+
alias select find_all
|
562
|
+
|
563
|
+
# <!-- rdoc-file=enum.c -->
|
564
|
+
# Returns an array containing elements selected by the block.
|
565
|
+
#
|
566
|
+
# With a block given, calls the block with successive elements; returns an array
|
567
|
+
# of those elements for which the block returns a truthy value:
|
568
|
+
#
|
569
|
+
# (0..9).select {|element| element % 3 == 0 } # => [0, 3, 6, 9]
|
570
|
+
# a = {foo: 0, bar: 1, baz: 2}.select {|key, value| key.start_with?('b') }
|
571
|
+
# a # => {:bar=>1, :baz=>2}
|
572
|
+
#
|
573
|
+
# With no block given, returns an Enumerator.
|
574
|
+
#
|
575
|
+
# Related: #reject.
|
576
|
+
#
|
577
|
+
alias filter find_all
|
578
|
+
|
579
|
+
# <!--
|
580
|
+
# rdoc-file=enum.c
|
581
|
+
# - find_index(object) -> integer or nil
|
582
|
+
# - find_index {|element| ... } -> integer or nil
|
583
|
+
# - find_index -> enumerator
|
584
|
+
# -->
|
585
|
+
# Returns the index of the first element that meets a specified criterion, or
|
586
|
+
# `nil` if no such element is found.
|
587
|
+
#
|
588
|
+
# With argument `object` given, returns the index of the first element that is
|
589
|
+
# `==` `object`:
|
590
|
+
#
|
591
|
+
# ['a', 'b', 'c', 'b'].find_index('b') # => 1
|
592
|
+
#
|
593
|
+
# With a block given, calls the block with successive elements; returns the
|
594
|
+
# first element for which the block returns a truthy value:
|
595
|
+
#
|
596
|
+
# ['a', 'b', 'c', 'b'].find_index {|element| element.start_with?('b') } # => 1
|
597
|
+
# {foo: 0, bar: 1, baz: 2}.find_index {|key, value| value > 1 } # => 2
|
598
|
+
#
|
599
|
+
# With no argument and no block given, returns an Enumerator.
|
600
|
+
#
|
601
|
+
def find_index: (untyped value) -> Integer?
|
602
|
+
| () { (Elem) -> boolish } -> Integer?
|
603
|
+
| () -> ::Enumerator[Elem, Integer?]
|
604
|
+
|
605
|
+
# <!--
|
606
|
+
# rdoc-file=enum.c
|
607
|
+
# - first -> element or nil
|
608
|
+
# - first(n) -> array
|
609
|
+
# -->
|
610
|
+
# Returns the first element or elements.
|
611
|
+
#
|
612
|
+
# With no argument, returns the first element, or `nil` if there is none:
|
613
|
+
#
|
614
|
+
# (1..4).first # => 1
|
615
|
+
# %w[a b c].first # => "a"
|
616
|
+
# {foo: 1, bar: 1, baz: 2}.first # => [:foo, 1]
|
617
|
+
# [].first # => nil
|
618
|
+
#
|
619
|
+
# With integer argument `n`, returns an array containing the first `n` elements
|
620
|
+
# that exist:
|
621
|
+
#
|
622
|
+
# (1..4).first(2) # => [1, 2]
|
623
|
+
# %w[a b c d].first(3) # => ["a", "b", "c"]
|
624
|
+
# %w[a b c d].first(50) # => ["a", "b", "c", "d"]
|
625
|
+
# {foo: 1, bar: 1, baz: 2}.first(2) # => [[:foo, 1], [:bar, 1]]
|
626
|
+
# [].first(2) # => []
|
627
|
+
#
|
628
|
+
def first: () -> Elem?
|
629
|
+
| (_ToInt n) -> ::Array[Elem]
|
630
|
+
|
631
|
+
# <!--
|
632
|
+
# rdoc-file=enum.c
|
633
|
+
# - grep(pattern) -> array
|
634
|
+
# - grep(pattern) {|element| ... } -> array
|
635
|
+
# -->
|
636
|
+
# Returns an array of objects based elements of `self` that match the given
|
637
|
+
# pattern.
|
638
|
+
#
|
639
|
+
# With no block given, returns an array containing each element for which
|
640
|
+
# `pattern === element` is `true`:
|
641
|
+
#
|
642
|
+
# a = ['foo', 'bar', 'car', 'moo']
|
643
|
+
# a.grep(/ar/) # => ["bar", "car"]
|
644
|
+
# (1..10).grep(3..8) # => [3, 4, 5, 6, 7, 8]
|
645
|
+
# ['a', 'b', 0, 1].grep(Integer) # => [0, 1]
|
646
|
+
#
|
647
|
+
# With a block given, calls the block with each matching element and returns an
|
648
|
+
# array containing each object returned by the block:
|
649
|
+
#
|
650
|
+
# a = ['foo', 'bar', 'car', 'moo']
|
651
|
+
# a.grep(/ar/) {|element| element.upcase } # => ["BAR", "CAR"]
|
652
|
+
#
|
653
|
+
# Related: #grep_v.
|
654
|
+
#
|
655
|
+
def grep: (untyped arg0) -> ::Array[Elem]
|
656
|
+
| [U] (untyped arg0) { (Elem arg0) -> U } -> ::Array[U]
|
657
|
+
|
658
|
+
# <!--
|
659
|
+
# rdoc-file=enum.c
|
660
|
+
# - grep_v(pattern) -> array
|
661
|
+
# - grep_v(pattern) {|element| ... } -> array
|
662
|
+
# -->
|
663
|
+
# Returns an array of objects based on elements of `self` that *don't* match the
|
664
|
+
# given pattern.
|
665
|
+
#
|
666
|
+
# With no block given, returns an array containing each element for which
|
667
|
+
# `pattern === element` is `false`:
|
668
|
+
#
|
669
|
+
# a = ['foo', 'bar', 'car', 'moo']
|
670
|
+
# a.grep_v(/ar/) # => ["foo", "moo"]
|
671
|
+
# (1..10).grep_v(3..8) # => [1, 2, 9, 10]
|
672
|
+
# ['a', 'b', 0, 1].grep_v(Integer) # => ["a", "b"]
|
673
|
+
#
|
674
|
+
# With a block given, calls the block with each non-matching element and returns
|
675
|
+
# an array containing each object returned by the block:
|
676
|
+
#
|
677
|
+
# a = ['foo', 'bar', 'car', 'moo']
|
678
|
+
# a.grep_v(/ar/) {|element| element.upcase } # => ["FOO", "MOO"]
|
679
|
+
#
|
680
|
+
# Related: #grep.
|
681
|
+
#
|
682
|
+
def grep_v: (untyped) -> ::Array[Elem]
|
683
|
+
| [U] (untyped) { (Elem) -> U } -> ::Array[U]
|
684
|
+
|
685
|
+
# <!--
|
686
|
+
# rdoc-file=enum.c
|
687
|
+
# - group_by {|element| ... } -> hash
|
688
|
+
# - group_by -> enumerator
|
689
|
+
# -->
|
690
|
+
# With a block given returns a hash:
|
691
|
+
#
|
692
|
+
# * Each key is a return value from the block.
|
693
|
+
# * Each value is an array of those elements for which the block returned that
|
694
|
+
# key.
|
695
|
+
#
|
696
|
+
# Examples:
|
697
|
+
#
|
698
|
+
# g = (1..6).group_by {|i| i%3 }
|
699
|
+
# g # => {1=>[1, 4], 2=>[2, 5], 0=>[3, 6]}
|
700
|
+
# h = {foo: 0, bar: 1, baz: 0, bat: 1}
|
701
|
+
# g = h.group_by {|key, value| value }
|
702
|
+
# g # => {0=>[[:foo, 0], [:baz, 0]], 1=>[[:bar, 1], [:bat, 1]]}
|
703
|
+
#
|
704
|
+
# With no block given, returns an Enumerator.
|
705
|
+
#
|
706
|
+
def group_by: [U] () { (Elem arg0) -> U } -> ::Hash[U, ::Array[Elem]]
|
707
|
+
| () -> ::Enumerator[Elem, ::Array[Elem]]
|
708
|
+
|
709
|
+
# <!-- rdoc-file=enum.c -->
|
710
|
+
# Returns whether for any element `object == element`:
|
711
|
+
#
|
712
|
+
# (1..4).include?(2) # => true
|
713
|
+
# (1..4).include?(5) # => false
|
714
|
+
# (1..4).include?('2') # => false
|
715
|
+
# %w[a b c d].include?('b') # => true
|
716
|
+
# %w[a b c d].include?('2') # => false
|
717
|
+
# {foo: 0, bar: 1, baz: 2}.include?(:foo) # => true
|
718
|
+
# {foo: 0, bar: 1, baz: 2}.include?('foo') # => false
|
719
|
+
# {foo: 0, bar: 1, baz: 2}.include?(0) # => false
|
720
|
+
#
|
721
|
+
def include?: (Elem arg0) -> bool
|
722
|
+
|
723
|
+
# <!--
|
724
|
+
# rdoc-file=enum.c
|
725
|
+
# - inject(symbol) -> object
|
726
|
+
# - inject(initial_value, symbol) -> object
|
727
|
+
# - inject {|memo, value| ... } -> object
|
728
|
+
# - inject(initial_value) {|memo, value| ... } -> object
|
729
|
+
# -->
|
730
|
+
# Returns the result of applying a reducer to an initial value and the first
|
731
|
+
# element of the Enumerable. It then takes the result and applies the function
|
732
|
+
# to it and the second element of the collection, and so on. The return value is
|
733
|
+
# the result returned by the final call to the function.
|
734
|
+
#
|
735
|
+
# You can think of
|
736
|
+
#
|
737
|
+
# [ a, b, c, d ].inject(i) { |r, v| fn(r, v) }
|
738
|
+
#
|
739
|
+
# as being
|
740
|
+
#
|
741
|
+
# fn(fn(fn(fn(i, a), b), c), d)
|
742
|
+
#
|
743
|
+
# In a way the `inject` function *injects* the function between the elements of
|
744
|
+
# the enumerable.
|
745
|
+
#
|
746
|
+
# `inject` is aliased as `reduce`. You use it when you want to *reduce* a
|
747
|
+
# collection to a single value.
|
748
|
+
#
|
749
|
+
# **The Calling Sequences**
|
750
|
+
#
|
751
|
+
# Let's start with the most verbose:
|
752
|
+
#
|
753
|
+
# enum.inject(initial_value) do |result, next_value|
|
754
|
+
# # do something with +result+ and +next_value+
|
755
|
+
# # the value returned by the block becomes the
|
756
|
+
# # value passed in to the next iteration
|
757
|
+
# # as +result+
|
758
|
+
# end
|
759
|
+
#
|
760
|
+
# For example:
|
761
|
+
#
|
762
|
+
# product = [ 2, 3, 4 ].inject(1) do |result, next_value|
|
763
|
+
# result * next_value
|
764
|
+
# end
|
765
|
+
# product #=> 24
|
766
|
+
#
|
767
|
+
# When this runs, the block is first called with `1` (the initial value) and `2`
|
768
|
+
# (the first element of the array). The block returns `1*2`, so on the next
|
769
|
+
# iteration the block is called with `2` (the previous result) and `3`. The
|
770
|
+
# block returns `6`, and is called one last time with `6` and `4`. The result of
|
771
|
+
# the block, `24` becomes the value returned by `inject`. This code returns the
|
772
|
+
# product of the elements in the enumerable.
|
773
|
+
#
|
774
|
+
# **First Shortcut: Default Initial value**
|
775
|
+
#
|
776
|
+
# In the case of the previous example, the initial value, `1`, wasn't really
|
777
|
+
# necessary: the calculation of the product of a list of numbers is
|
778
|
+
# self-contained.
|
779
|
+
#
|
780
|
+
# In these circumstances, you can omit the `initial_value` parameter. `inject`
|
781
|
+
# will then initially call the block with the first element of the collection as
|
782
|
+
# the `result` parameter and the second element as the `next_value`.
|
783
|
+
#
|
784
|
+
# [ 2, 3, 4 ].inject do |result, next_value|
|
785
|
+
# result * next_value
|
786
|
+
# end
|
787
|
+
#
|
788
|
+
# This shortcut is convenient, but can only be used when the block produces a
|
789
|
+
# result which can be passed back to it as a first parameter.
|
790
|
+
#
|
791
|
+
# Here's an example where that's not the case: it returns a hash where the keys
|
792
|
+
# are words and the values are the number of occurrences of that word in the
|
793
|
+
# enumerable.
|
794
|
+
#
|
795
|
+
# freqs = File.read("README.md")
|
796
|
+
# .scan(/\w{2,}/)
|
797
|
+
# .reduce(Hash.new(0)) do |counts, word|
|
798
|
+
# counts[word] += 1
|
799
|
+
# counts
|
800
|
+
# end
|
801
|
+
# freqs #=> {"Actions"=>4,
|
802
|
+
# "Status"=>5,
|
803
|
+
# "MinGW"=>3,
|
804
|
+
# "https"=>27,
|
805
|
+
# "github"=>10,
|
806
|
+
# "com"=>15, ...
|
807
|
+
#
|
808
|
+
# Note that the last line of the block is just the word `counts`. This ensures
|
809
|
+
# the return value of the block is the result that's being calculated.
|
810
|
+
#
|
811
|
+
# **Second Shortcut: a Reducer function**
|
812
|
+
#
|
813
|
+
# A *reducer function* is a function that takes a partial result and the next
|
814
|
+
# value, returning the next partial result. The block that is given to `inject`
|
815
|
+
# is a reducer.
|
816
|
+
#
|
817
|
+
# You can also write a reducer as a function and pass the name of that function
|
818
|
+
# (as a symbol) to `inject`. However, for this to work, the function
|
819
|
+
#
|
820
|
+
# 1. Must be defined on the type of the result value
|
821
|
+
# 2. Must accept a single parameter, the next value in the collection, and
|
822
|
+
# 3. Must return an updated result which will also implement the function.
|
823
|
+
#
|
824
|
+
# Here's an example that adds elements to a string. The two calls invoke the
|
825
|
+
# functions String#concat and String#+ on the result so far, passing it the next
|
826
|
+
# value.
|
827
|
+
#
|
828
|
+
# s = [ "cat", " ", "dog" ].inject("", :concat)
|
829
|
+
# s #=> "cat dog"
|
830
|
+
# s = [ "cat", " ", "dog" ].inject("The result is:", :+)
|
831
|
+
# s #=> "The result is: cat dog"
|
832
|
+
#
|
833
|
+
# Here's a more complex example when the result object maintains state of a
|
834
|
+
# different type to the enumerable elements.
|
835
|
+
#
|
836
|
+
# class Turtle
|
837
|
+
#
|
838
|
+
# def initialize
|
839
|
+
# @x = @y = 0
|
840
|
+
# end
|
841
|
+
#
|
842
|
+
# def move(dir)
|
843
|
+
# case dir
|
844
|
+
# when "n" then @y += 1
|
845
|
+
# when "s" then @y -= 1
|
846
|
+
# when "e" then @x += 1
|
847
|
+
# when "w" then @x -= 1
|
848
|
+
# end
|
849
|
+
# self
|
850
|
+
# end
|
851
|
+
# end
|
852
|
+
#
|
853
|
+
# position = "nnneesw".chars.reduce(Turtle.new, :move)
|
854
|
+
# position #=>> #<Turtle:0x00000001052f4698 @y=2, @x=1>
|
855
|
+
#
|
856
|
+
# **Third Shortcut: Reducer With no Initial Value**
|
857
|
+
#
|
858
|
+
# If your reducer returns a value that it can accept as a parameter, then you
|
859
|
+
# don't have to pass in an initial value. Here `:*` is the name of the *times*
|
860
|
+
# function:
|
861
|
+
#
|
862
|
+
# product = [ 2, 3, 4 ].inject(:*)
|
863
|
+
# product # => 24
|
864
|
+
#
|
865
|
+
# String concatenation again:
|
866
|
+
#
|
867
|
+
# s = [ "cat", " ", "dog" ].inject(:+)
|
868
|
+
# s #=> "cat dog"
|
869
|
+
#
|
870
|
+
# And an example that converts a hash to an array of two-element subarrays.
|
871
|
+
#
|
872
|
+
# nested = {foo: 0, bar: 1}.inject([], :push)
|
873
|
+
# nested # => [[:foo, 0], [:bar, 1]]
|
874
|
+
#
|
875
|
+
def inject: (untyped init, Symbol method) -> untyped
|
876
|
+
| (Symbol method) -> untyped
|
877
|
+
| [A] (A initial) { (A, Elem) -> A } -> A
|
878
|
+
| () { (Elem, Elem) -> Elem } -> Elem
|
879
|
+
|
880
|
+
# <!--
|
881
|
+
# rdoc-file=enum.c
|
882
|
+
# - max -> element
|
883
|
+
# - max(n) -> array
|
884
|
+
# - max {|a, b| ... } -> element
|
885
|
+
# - max(n) {|a, b| ... } -> array
|
886
|
+
# -->
|
887
|
+
# Returns the element with the maximum element according to a given criterion.
|
888
|
+
# The ordering of equal elements is indeterminate and may be unstable.
|
889
|
+
#
|
890
|
+
# With no argument and no block, returns the maximum element, using the
|
891
|
+
# elements' own method `#<=>` for comparison:
|
892
|
+
#
|
893
|
+
# (1..4).max # => 4
|
894
|
+
# (-4..-1).max # => -1
|
895
|
+
# %w[d c b a].max # => "d"
|
896
|
+
# {foo: 0, bar: 1, baz: 2}.max # => [:foo, 0]
|
897
|
+
# [].max # => nil
|
898
|
+
#
|
899
|
+
# With positive integer argument `n` given, and no block, returns an array
|
900
|
+
# containing the first `n` maximum elements that exist:
|
901
|
+
#
|
902
|
+
# (1..4).max(2) # => [4, 3]
|
903
|
+
# (-4..-1).max(2) # => [-1, -2]
|
904
|
+
# %w[d c b a].max(2) # => ["d", "c"]
|
905
|
+
# {foo: 0, bar: 1, baz: 2}.max(2) # => [[:foo, 0], [:baz, 2]]
|
906
|
+
# [].max(2) # => []
|
907
|
+
#
|
908
|
+
# With a block given, the block determines the maximum elements. The block is
|
909
|
+
# called with two elements `a` and `b`, and must return:
|
910
|
+
#
|
911
|
+
# * A negative integer if `a < b`.
|
912
|
+
# * Zero if `a == b`.
|
913
|
+
# * A positive integer if `a > b`.
|
914
|
+
#
|
915
|
+
# With a block given and no argument, returns the maximum element as determined
|
916
|
+
# by the block:
|
917
|
+
#
|
918
|
+
# %w[xxx x xxxx xx].max {|a, b| a.size <=> b.size } # => "xxxx"
|
919
|
+
# h = {foo: 0, bar: 1, baz: 2}
|
920
|
+
# h.max {|pair1, pair2| pair1[1] <=> pair2[1] } # => [:baz, 2]
|
921
|
+
# [].max {|a, b| a <=> b } # => nil
|
922
|
+
#
|
923
|
+
# With a block given and positive integer argument `n` given, returns an array
|
924
|
+
# containing the first `n` maximum elements that exist, as determined by the
|
925
|
+
# block.
|
926
|
+
#
|
927
|
+
# %w[xxx x xxxx xx].max(2) {|a, b| a.size <=> b.size } # => ["xxxx", "xxx"]
|
928
|
+
# h = {foo: 0, bar: 1, baz: 2}
|
929
|
+
# h.max(2) {|pair1, pair2| pair1[1] <=> pair2[1] }
|
930
|
+
# # => [[:baz, 2], [:bar, 1]]
|
931
|
+
# [].max(2) {|a, b| a <=> b } # => []
|
932
|
+
#
|
933
|
+
# Related: #min, #minmax, #max_by.
|
934
|
+
#
|
935
|
+
def max: () -> Elem?
|
936
|
+
| () { (Elem arg0, Elem arg1) -> Integer } -> Elem?
|
937
|
+
| (Integer arg0) -> ::Array[Elem]
|
938
|
+
| (Integer arg0) { (Elem arg0, Elem arg1) -> Integer } -> ::Array[Elem]
|
939
|
+
|
940
|
+
# <!--
|
941
|
+
# rdoc-file=enum.c
|
942
|
+
# - max_by {|element| ... } -> element
|
943
|
+
# - max_by(n) {|element| ... } -> array
|
944
|
+
# - max_by -> enumerator
|
945
|
+
# - max_by(n) -> enumerator
|
946
|
+
# -->
|
947
|
+
# Returns the elements for which the block returns the maximum values.
|
948
|
+
#
|
949
|
+
# With a block given and no argument, returns the element for which the block
|
950
|
+
# returns the maximum value:
|
951
|
+
#
|
952
|
+
# (1..4).max_by {|element| -element } # => 1
|
953
|
+
# %w[a b c d].max_by {|element| -element.ord } # => "a"
|
954
|
+
# {foo: 0, bar: 1, baz: 2}.max_by {|key, value| -value } # => [:foo, 0]
|
955
|
+
# [].max_by {|element| -element } # => nil
|
956
|
+
#
|
957
|
+
# With a block given and positive integer argument `n` given, returns an array
|
958
|
+
# containing the `n` elements for which the block returns maximum values:
|
959
|
+
#
|
960
|
+
# (1..4).max_by(2) {|element| -element }
|
961
|
+
# # => [1, 2]
|
962
|
+
# %w[a b c d].max_by(2) {|element| -element.ord }
|
963
|
+
# # => ["a", "b"]
|
964
|
+
# {foo: 0, bar: 1, baz: 2}.max_by(2) {|key, value| -value }
|
965
|
+
# # => [[:foo, 0], [:bar, 1]]
|
966
|
+
# [].max_by(2) {|element| -element }
|
967
|
+
# # => []
|
968
|
+
#
|
969
|
+
# Returns an Enumerator if no block is given.
|
970
|
+
#
|
971
|
+
# Related: #max, #minmax, #min_by.
|
972
|
+
#
|
973
|
+
def max_by: () -> ::Enumerator[Elem, Elem?]
|
974
|
+
| () { (Elem arg0) -> (Comparable | ::Array[untyped]) } -> Elem?
|
975
|
+
| (Integer arg0) -> ::Enumerator[Elem, ::Array[Elem]]
|
976
|
+
| (Integer arg0) { (Elem arg0) -> (Comparable | ::Array[untyped]) } -> ::Array[Elem]
|
977
|
+
|
978
|
+
# <!--
|
979
|
+
# rdoc-file=enum.c
|
980
|
+
# - min -> element
|
981
|
+
# - min(n) -> array
|
982
|
+
# - min {|a, b| ... } -> element
|
983
|
+
# - min(n) {|a, b| ... } -> array
|
984
|
+
# -->
|
985
|
+
# Returns the element with the minimum element according to a given criterion.
|
986
|
+
# The ordering of equal elements is indeterminate and may be unstable.
|
987
|
+
#
|
988
|
+
# With no argument and no block, returns the minimum element, using the
|
989
|
+
# elements' own method `#<=>` for comparison:
|
990
|
+
#
|
991
|
+
# (1..4).min # => 1
|
992
|
+
# (-4..-1).min # => -4
|
993
|
+
# %w[d c b a].min # => "a"
|
994
|
+
# {foo: 0, bar: 1, baz: 2}.min # => [:bar, 1]
|
995
|
+
# [].min # => nil
|
996
|
+
#
|
997
|
+
# With positive integer argument `n` given, and no block, returns an array
|
998
|
+
# containing the first `n` minimum elements that exist:
|
999
|
+
#
|
1000
|
+
# (1..4).min(2) # => [1, 2]
|
1001
|
+
# (-4..-1).min(2) # => [-4, -3]
|
1002
|
+
# %w[d c b a].min(2) # => ["a", "b"]
|
1003
|
+
# {foo: 0, bar: 1, baz: 2}.min(2) # => [[:bar, 1], [:baz, 2]]
|
1004
|
+
# [].min(2) # => []
|
1005
|
+
#
|
1006
|
+
# With a block given, the block determines the minimum elements. The block is
|
1007
|
+
# called with two elements `a` and `b`, and must return:
|
1008
|
+
#
|
1009
|
+
# * A negative integer if `a < b`.
|
1010
|
+
# * Zero if `a == b`.
|
1011
|
+
# * A positive integer if `a > b`.
|
1012
|
+
#
|
1013
|
+
# With a block given and no argument, returns the minimum element as determined
|
1014
|
+
# by the block:
|
1015
|
+
#
|
1016
|
+
# %w[xxx x xxxx xx].min {|a, b| a.size <=> b.size } # => "x"
|
1017
|
+
# h = {foo: 0, bar: 1, baz: 2}
|
1018
|
+
# h.min {|pair1, pair2| pair1[1] <=> pair2[1] } # => [:foo, 0]
|
1019
|
+
# [].min {|a, b| a <=> b } # => nil
|
1020
|
+
#
|
1021
|
+
# With a block given and positive integer argument `n` given, returns an array
|
1022
|
+
# containing the first `n` minimum elements that exist, as determined by the
|
1023
|
+
# block.
|
1024
|
+
#
|
1025
|
+
# %w[xxx x xxxx xx].min(2) {|a, b| a.size <=> b.size } # => ["x", "xx"]
|
1026
|
+
# h = {foo: 0, bar: 1, baz: 2}
|
1027
|
+
# h.min(2) {|pair1, pair2| pair1[1] <=> pair2[1] }
|
1028
|
+
# # => [[:foo, 0], [:bar, 1]]
|
1029
|
+
# [].min(2) {|a, b| a <=> b } # => []
|
1030
|
+
#
|
1031
|
+
# Related: #min_by, #minmax, #max.
|
1032
|
+
#
|
1033
|
+
def min: () -> Elem?
|
1034
|
+
| () { (Elem arg0, Elem arg1) -> Integer } -> Elem?
|
1035
|
+
| (Integer arg0) -> ::Array[Elem]
|
1036
|
+
| (Integer arg0) { (Elem arg0, Elem arg1) -> Integer } -> ::Array[Elem]
|
1037
|
+
|
1038
|
+
# <!--
|
1039
|
+
# rdoc-file=enum.c
|
1040
|
+
# - min_by {|element| ... } -> element
|
1041
|
+
# - min_by(n) {|element| ... } -> array
|
1042
|
+
# - min_by -> enumerator
|
1043
|
+
# - min_by(n) -> enumerator
|
1044
|
+
# -->
|
1045
|
+
# Returns the elements for which the block returns the minimum values.
|
1046
|
+
#
|
1047
|
+
# With a block given and no argument, returns the element for which the block
|
1048
|
+
# returns the minimum value:
|
1049
|
+
#
|
1050
|
+
# (1..4).min_by {|element| -element } # => 4
|
1051
|
+
# %w[a b c d].min_by {|element| -element.ord } # => "d"
|
1052
|
+
# {foo: 0, bar: 1, baz: 2}.min_by {|key, value| -value } # => [:baz, 2]
|
1053
|
+
# [].min_by {|element| -element } # => nil
|
1054
|
+
#
|
1055
|
+
# With a block given and positive integer argument `n` given, returns an array
|
1056
|
+
# containing the `n` elements for which the block returns minimum values:
|
1057
|
+
#
|
1058
|
+
# (1..4).min_by(2) {|element| -element }
|
1059
|
+
# # => [4, 3]
|
1060
|
+
# %w[a b c d].min_by(2) {|element| -element.ord }
|
1061
|
+
# # => ["d", "c"]
|
1062
|
+
# {foo: 0, bar: 1, baz: 2}.min_by(2) {|key, value| -value }
|
1063
|
+
# # => [[:baz, 2], [:bar, 1]]
|
1064
|
+
# [].min_by(2) {|element| -element }
|
1065
|
+
# # => []
|
1066
|
+
#
|
1067
|
+
# Returns an Enumerator if no block is given.
|
1068
|
+
#
|
1069
|
+
# Related: #min, #minmax, #max_by.
|
1070
|
+
#
|
1071
|
+
def min_by: () -> ::Enumerator[Elem, Elem?]
|
1072
|
+
| () { (Elem arg0) -> (Comparable | ::Array[untyped]) } -> Elem?
|
1073
|
+
| (Integer arg0) -> ::Enumerator[Elem, ::Array[Elem]]
|
1074
|
+
| (Integer arg0) { (Elem arg0) -> (Comparable | ::Array[untyped]) } -> ::Array[Elem]
|
1075
|
+
|
1076
|
+
# <!--
|
1077
|
+
# rdoc-file=enum.c
|
1078
|
+
# - minmax -> [minimum, maximum]
|
1079
|
+
# - minmax {|a, b| ... } -> [minimum, maximum]
|
1080
|
+
# -->
|
1081
|
+
# Returns a 2-element array containing the minimum and maximum elements
|
1082
|
+
# according to a given criterion. The ordering of equal elements is
|
1083
|
+
# indeterminate and may be unstable.
|
1084
|
+
#
|
1085
|
+
# With no argument and no block, returns the minimum and maximum elements, using
|
1086
|
+
# the elements' own method `#<=>` for comparison:
|
1087
|
+
#
|
1088
|
+
# (1..4).minmax # => [1, 4]
|
1089
|
+
# (-4..-1).minmax # => [-4, -1]
|
1090
|
+
# %w[d c b a].minmax # => ["a", "d"]
|
1091
|
+
# {foo: 0, bar: 1, baz: 2}.minmax # => [[:bar, 1], [:foo, 0]]
|
1092
|
+
# [].minmax # => [nil, nil]
|
1093
|
+
#
|
1094
|
+
# With a block given, returns the minimum and maximum elements as determined by
|
1095
|
+
# the block:
|
1096
|
+
#
|
1097
|
+
# %w[xxx x xxxx xx].minmax {|a, b| a.size <=> b.size } # => ["x", "xxxx"]
|
1098
|
+
# h = {foo: 0, bar: 1, baz: 2}
|
1099
|
+
# h.minmax {|pair1, pair2| pair1[1] <=> pair2[1] }
|
1100
|
+
# # => [[:foo, 0], [:baz, 2]]
|
1101
|
+
# [].minmax {|a, b| a <=> b } # => [nil, nil]
|
1102
|
+
#
|
1103
|
+
# Related: #min, #max, #minmax_by.
|
1104
|
+
#
|
1105
|
+
def minmax: () -> [ Elem?, Elem? ]
|
1106
|
+
| () { (Elem arg0, Elem arg1) -> Integer } -> [ Elem?, Elem? ]
|
1107
|
+
|
1108
|
+
# <!--
|
1109
|
+
# rdoc-file=enum.c
|
1110
|
+
# - minmax_by {|element| ... } -> [minimum, maximum]
|
1111
|
+
# - minmax_by -> enumerator
|
1112
|
+
# -->
|
1113
|
+
# Returns a 2-element array containing the elements for which the block returns
|
1114
|
+
# minimum and maximum values:
|
1115
|
+
#
|
1116
|
+
# (1..4).minmax_by {|element| -element }
|
1117
|
+
# # => [4, 1]
|
1118
|
+
# %w[a b c d].minmax_by {|element| -element.ord }
|
1119
|
+
# # => ["d", "a"]
|
1120
|
+
# {foo: 0, bar: 1, baz: 2}.minmax_by {|key, value| -value }
|
1121
|
+
# # => [[:baz, 2], [:foo, 0]]
|
1122
|
+
# [].minmax_by {|element| -element }
|
1123
|
+
# # => [nil, nil]
|
1124
|
+
#
|
1125
|
+
# Returns an Enumerator if no block is given.
|
1126
|
+
#
|
1127
|
+
# Related: #max_by, #minmax, #min_by.
|
1128
|
+
#
|
1129
|
+
def minmax_by: () -> [ Elem?, Elem? ]
|
1130
|
+
| () { (Elem arg0) -> (Comparable | ::Array[untyped]) } -> [ Elem?, Elem? ]
|
1131
|
+
|
1132
|
+
# <!--
|
1133
|
+
# rdoc-file=enum.c
|
1134
|
+
# - none? -> true or false
|
1135
|
+
# - none?(pattern) -> true or false
|
1136
|
+
# - none? {|element| ... } -> true or false
|
1137
|
+
# -->
|
1138
|
+
# Returns whether no element meets a given criterion.
|
1139
|
+
#
|
1140
|
+
# With no argument and no block, returns whether no element is truthy:
|
1141
|
+
#
|
1142
|
+
# (1..4).none? # => false
|
1143
|
+
# [nil, false].none? # => true
|
1144
|
+
# {foo: 0}.none? # => false
|
1145
|
+
# {foo: 0, bar: 1}.none? # => false
|
1146
|
+
# [].none? # => true
|
1147
|
+
#
|
1148
|
+
# With argument `pattern` and no block, returns whether for no element
|
1149
|
+
# `element`, `pattern === element`:
|
1150
|
+
#
|
1151
|
+
# [nil, false, 1.1].none?(Integer) # => true
|
1152
|
+
# %w[bar baz bat bam].none?(/m/) # => false
|
1153
|
+
# %w[bar baz bat bam].none?(/foo/) # => true
|
1154
|
+
# %w[bar baz bat bam].none?('ba') # => true
|
1155
|
+
# {foo: 0, bar: 1, baz: 2}.none?(Hash) # => true
|
1156
|
+
# {foo: 0}.none?(Array) # => false
|
1157
|
+
# [].none?(Integer) # => true
|
1158
|
+
#
|
1159
|
+
# With a block given, returns whether the block returns a truthy value for no
|
1160
|
+
# element:
|
1161
|
+
#
|
1162
|
+
# (1..4).none? {|element| element < 1 } # => true
|
1163
|
+
# (1..4).none? {|element| element < 2 } # => false
|
1164
|
+
# {foo: 0, bar: 1, baz: 2}.none? {|key, value| value < 0 } # => true
|
1165
|
+
# {foo: 0, bar: 1, baz: 2}.none? {|key, value| value < 1 } # => false
|
1166
|
+
#
|
1167
|
+
# Related: #one?, #all?, #any?.
|
1168
|
+
#
|
1169
|
+
def none?: () -> bool
|
1170
|
+
| () { (Elem) -> boolish } -> bool
|
1171
|
+
|
1172
|
+
# <!--
|
1173
|
+
# rdoc-file=enum.c
|
1174
|
+
# - one? -> true or false
|
1175
|
+
# - one?(pattern) -> true or false
|
1176
|
+
# - one? {|element| ... } -> true or false
|
1177
|
+
# -->
|
1178
|
+
# Returns whether exactly one element meets a given criterion.
|
1179
|
+
#
|
1180
|
+
# With no argument and no block, returns whether exactly one element is truthy:
|
1181
|
+
#
|
1182
|
+
# (1..1).one? # => true
|
1183
|
+
# [1, nil, false].one? # => true
|
1184
|
+
# (1..4).one? # => false
|
1185
|
+
# {foo: 0}.one? # => true
|
1186
|
+
# {foo: 0, bar: 1}.one? # => false
|
1187
|
+
# [].one? # => false
|
1188
|
+
#
|
1189
|
+
# With argument `pattern` and no block, returns whether for exactly one element
|
1190
|
+
# `element`, `pattern === element`:
|
1191
|
+
#
|
1192
|
+
# [nil, false, 0].one?(Integer) # => true
|
1193
|
+
# [nil, false, 0].one?(Numeric) # => true
|
1194
|
+
# [nil, false, 0].one?(Float) # => false
|
1195
|
+
# %w[bar baz bat bam].one?(/m/) # => true
|
1196
|
+
# %w[bar baz bat bam].one?(/foo/) # => false
|
1197
|
+
# %w[bar baz bat bam].one?('ba') # => false
|
1198
|
+
# {foo: 0, bar: 1, baz: 2}.one?(Array) # => false
|
1199
|
+
# {foo: 0}.one?(Array) # => true
|
1200
|
+
# [].one?(Integer) # => false
|
1201
|
+
#
|
1202
|
+
# With a block given, returns whether the block returns a truthy value for
|
1203
|
+
# exactly one element:
|
1204
|
+
#
|
1205
|
+
# (1..4).one? {|element| element < 2 } # => true
|
1206
|
+
# (1..4).one? {|element| element < 1 } # => false
|
1207
|
+
# {foo: 0, bar: 1, baz: 2}.one? {|key, value| value < 1 } # => true
|
1208
|
+
# {foo: 0, bar: 1, baz: 2}.one? {|key, value| value < 2 } # => false
|
1209
|
+
#
|
1210
|
+
# Related: #none?, #all?, #any?.
|
1211
|
+
#
|
1212
|
+
def one?: () -> bool
|
1213
|
+
| () { (Elem) -> boolish } -> bool
|
1214
|
+
|
1215
|
+
# <!--
|
1216
|
+
# rdoc-file=enum.c
|
1217
|
+
# - partition {|element| ... } -> [true_array, false_array]
|
1218
|
+
# - partition -> enumerator
|
1219
|
+
# -->
|
1220
|
+
# With a block given, returns an array of two arrays:
|
1221
|
+
#
|
1222
|
+
# * The first having those elements for which the block returns a truthy
|
1223
|
+
# value.
|
1224
|
+
# * The other having all other elements.
|
1225
|
+
#
|
1226
|
+
# Examples:
|
1227
|
+
#
|
1228
|
+
# p = (1..4).partition {|i| i.even? }
|
1229
|
+
# p # => [[2, 4], [1, 3]]
|
1230
|
+
# p = ('a'..'d').partition {|c| c < 'c' }
|
1231
|
+
# p # => [["a", "b"], ["c", "d"]]
|
1232
|
+
# h = {foo: 0, bar: 1, baz: 2, bat: 3}
|
1233
|
+
# p = h.partition {|key, value| key.start_with?('b') }
|
1234
|
+
# p # => [[[:bar, 1], [:baz, 2], [:bat, 3]], [[:foo, 0]]]
|
1235
|
+
# p = h.partition {|key, value| value < 2 }
|
1236
|
+
# p # => [[[:foo, 0], [:bar, 1]], [[:baz, 2], [:bat, 3]]]
|
1237
|
+
#
|
1238
|
+
# With no block given, returns an Enumerator.
|
1239
|
+
#
|
1240
|
+
# Related: Enumerable#group_by.
|
1241
|
+
#
|
1242
|
+
def partition: () { (Elem) -> boolish } -> [ ::Array[Elem], ::Array[Elem] ]
|
1243
|
+
| () -> ::Enumerator[Elem, [ ::Array[Elem], ::Array[Elem] ]]
|
1244
|
+
|
1245
|
+
# <!--
|
1246
|
+
# rdoc-file=enum.c
|
1247
|
+
# - reject {|element| ... } -> array
|
1248
|
+
# - reject -> enumerator
|
1249
|
+
# -->
|
1250
|
+
# Returns an array of objects rejected by the block.
|
1251
|
+
#
|
1252
|
+
# With a block given, calls the block with successive elements; returns an array
|
1253
|
+
# of those elements for which the block returns `nil` or `false`:
|
1254
|
+
#
|
1255
|
+
# (0..9).reject {|i| i * 2 if i.even? } # => [1, 3, 5, 7, 9]
|
1256
|
+
# {foo: 0, bar: 1, baz: 2}.reject {|key, value| key if value.odd? } # => {:foo=>0, :baz=>2}
|
1257
|
+
#
|
1258
|
+
# When no block given, returns an Enumerator.
|
1259
|
+
#
|
1260
|
+
# Related: #select.
|
1261
|
+
#
|
1262
|
+
def reject: () { (Elem) -> boolish } -> ::Array[Elem]
|
1263
|
+
| () -> ::Enumerator[Elem, ::Array[Elem]]
|
1264
|
+
|
1265
|
+
# <!--
|
1266
|
+
# rdoc-file=enum.c
|
1267
|
+
# - reverse_each(*args) {|element| ... } -> self
|
1268
|
+
# - reverse_each(*args) -> enumerator
|
1269
|
+
# -->
|
1270
|
+
# With a block given, calls the block with each element, but in reverse order;
|
1271
|
+
# returns `self`:
|
1272
|
+
#
|
1273
|
+
# a = []
|
1274
|
+
# (1..4).reverse_each {|element| a.push(-element) } # => 1..4
|
1275
|
+
# a # => [-4, -3, -2, -1]
|
1276
|
+
#
|
1277
|
+
# a = []
|
1278
|
+
# %w[a b c d].reverse_each {|element| a.push(element) }
|
1279
|
+
# # => ["a", "b", "c", "d"]
|
1280
|
+
# a # => ["d", "c", "b", "a"]
|
1281
|
+
#
|
1282
|
+
# a = []
|
1283
|
+
# h.reverse_each {|element| a.push(element) }
|
1284
|
+
# # => {:foo=>0, :bar=>1, :baz=>2}
|
1285
|
+
# a # => [[:baz, 2], [:bar, 1], [:foo, 0]]
|
1286
|
+
#
|
1287
|
+
# With no block given, returns an Enumerator.
|
1288
|
+
#
|
1289
|
+
def reverse_each: () { (Elem arg0) -> untyped } -> void
|
1290
|
+
| () -> ::Enumerator[Elem]
|
1291
|
+
|
1292
|
+
# <!--
|
1293
|
+
# rdoc-file=enum.c
|
1294
|
+
# - sort -> array
|
1295
|
+
# - sort {|a, b| ... } -> array
|
1296
|
+
# -->
|
1297
|
+
# Returns an array containing the sorted elements of `self`. The ordering of
|
1298
|
+
# equal elements is indeterminate and may be unstable.
|
1299
|
+
#
|
1300
|
+
# With no block given, the sort compares using the elements' own method `#<=>`:
|
1301
|
+
#
|
1302
|
+
# %w[b c a d].sort # => ["a", "b", "c", "d"]
|
1303
|
+
# {foo: 0, bar: 1, baz: 2}.sort # => [[:bar, 1], [:baz, 2], [:foo, 0]]
|
1304
|
+
#
|
1305
|
+
# With a block given, comparisons in the block determine the ordering. The block
|
1306
|
+
# is called with two elements `a` and `b`, and must return:
|
1307
|
+
#
|
1308
|
+
# * A negative integer if `a < b`.
|
1309
|
+
# * Zero if `a == b`.
|
1310
|
+
# * A positive integer if `a > b`.
|
1311
|
+
#
|
1312
|
+
# Examples:
|
1313
|
+
#
|
1314
|
+
# a = %w[b c a d]
|
1315
|
+
# a.sort {|a, b| b <=> a } # => ["d", "c", "b", "a"]
|
1316
|
+
# h = {foo: 0, bar: 1, baz: 2}
|
1317
|
+
# h.sort {|a, b| b <=> a } # => [[:foo, 0], [:baz, 2], [:bar, 1]]
|
1318
|
+
#
|
1319
|
+
# See also #sort_by. It implements a Schwartzian transform which is useful when
|
1320
|
+
# key computation or comparison is expensive.
|
1321
|
+
#
|
1322
|
+
def sort: () -> ::Array[Elem]
|
1323
|
+
| () { (Elem arg0, Elem arg1) -> Integer } -> ::Array[Elem]
|
1324
|
+
|
1325
|
+
# <!--
|
1326
|
+
# rdoc-file=enum.c
|
1327
|
+
# - sort_by {|element| ... } -> array
|
1328
|
+
# - sort_by -> enumerator
|
1329
|
+
# -->
|
1330
|
+
# With a block given, returns an array of elements of `self`, sorted according
|
1331
|
+
# to the value returned by the block for each element. The ordering of equal
|
1332
|
+
# elements is indeterminate and may be unstable.
|
1333
|
+
#
|
1334
|
+
# Examples:
|
1335
|
+
#
|
1336
|
+
# a = %w[xx xxx x xxxx]
|
1337
|
+
# a.sort_by {|s| s.size } # => ["x", "xx", "xxx", "xxxx"]
|
1338
|
+
# a.sort_by {|s| -s.size } # => ["xxxx", "xxx", "xx", "x"]
|
1339
|
+
# h = {foo: 2, bar: 1, baz: 0}
|
1340
|
+
# h.sort_by{|key, value| value } # => [[:baz, 0], [:bar, 1], [:foo, 2]]
|
1341
|
+
# h.sort_by{|key, value| key } # => [[:bar, 1], [:baz, 0], [:foo, 2]]
|
1342
|
+
#
|
1343
|
+
# With no block given, returns an Enumerator.
|
1344
|
+
#
|
1345
|
+
# The current implementation of #sort_by generates an array of tuples containing
|
1346
|
+
# the original collection element and the mapped value. This makes #sort_by
|
1347
|
+
# fairly expensive when the keysets are simple.
|
1348
|
+
#
|
1349
|
+
# require 'benchmark'
|
1350
|
+
#
|
1351
|
+
# a = (1..100000).map { rand(100000) }
|
1352
|
+
#
|
1353
|
+
# Benchmark.bm(10) do |b|
|
1354
|
+
# b.report("Sort") { a.sort }
|
1355
|
+
# b.report("Sort by") { a.sort_by { |a| a } }
|
1356
|
+
# end
|
1357
|
+
#
|
1358
|
+
# *produces:*
|
1359
|
+
#
|
1360
|
+
# user system total real
|
1361
|
+
# Sort 0.180000 0.000000 0.180000 ( 0.175469)
|
1362
|
+
# Sort by 1.980000 0.040000 2.020000 ( 2.013586)
|
1363
|
+
#
|
1364
|
+
# However, consider the case where comparing the keys is a non-trivial
|
1365
|
+
# operation. The following code sorts some files on modification time using the
|
1366
|
+
# basic #sort method.
|
1367
|
+
#
|
1368
|
+
# files = Dir["*"]
|
1369
|
+
# sorted = files.sort { |a, b| File.new(a).mtime <=> File.new(b).mtime }
|
1370
|
+
# sorted #=> ["mon", "tues", "wed", "thurs"]
|
1371
|
+
#
|
1372
|
+
# This sort is inefficient: it generates two new File objects during every
|
1373
|
+
# comparison. A slightly better technique is to use the Kernel#test method to
|
1374
|
+
# generate the modification times directly.
|
1375
|
+
#
|
1376
|
+
# files = Dir["*"]
|
1377
|
+
# sorted = files.sort { |a, b|
|
1378
|
+
# test(?M, a) <=> test(?M, b)
|
1379
|
+
# }
|
1380
|
+
# sorted #=> ["mon", "tues", "wed", "thurs"]
|
1381
|
+
#
|
1382
|
+
# This still generates many unnecessary Time objects. A more efficient technique
|
1383
|
+
# is to cache the sort keys (modification times in this case) before the sort.
|
1384
|
+
# Perl users often call this approach a Schwartzian transform, after Randal
|
1385
|
+
# Schwartz. We construct a temporary array, where each element is an array
|
1386
|
+
# containing our sort key along with the filename. We sort this array, and then
|
1387
|
+
# extract the filename from the result.
|
1388
|
+
#
|
1389
|
+
# sorted = Dir["*"].collect { |f|
|
1390
|
+
# [test(?M, f), f]
|
1391
|
+
# }.sort.collect { |f| f[1] }
|
1392
|
+
# sorted #=> ["mon", "tues", "wed", "thurs"]
|
1393
|
+
#
|
1394
|
+
# This is exactly what #sort_by does internally.
|
1395
|
+
#
|
1396
|
+
# sorted = Dir["*"].sort_by { |f| test(?M, f) }
|
1397
|
+
# sorted #=> ["mon", "tues", "wed", "thurs"]
|
1398
|
+
#
|
1399
|
+
# To produce the reverse of a specific order, the following can be used:
|
1400
|
+
#
|
1401
|
+
# ary.sort_by { ... }.reverse!
|
1402
|
+
#
|
1403
|
+
def sort_by: () { (Elem arg0) -> (Comparable | ::Array[untyped]) } -> ::Array[Elem]
|
1404
|
+
| () -> ::Enumerator[Elem, ::Array[Elem]]
|
1405
|
+
|
1406
|
+
# <!--
|
1407
|
+
# rdoc-file=enum.c
|
1408
|
+
# - take(n) -> array
|
1409
|
+
# -->
|
1410
|
+
# For non-negative integer `n`, returns the first `n` elements:
|
1411
|
+
#
|
1412
|
+
# r = (1..4)
|
1413
|
+
# r.take(2) # => [1, 2]
|
1414
|
+
# r.take(0) # => []
|
1415
|
+
#
|
1416
|
+
# h = {foo: 0, bar: 1, baz: 2, bat: 3}
|
1417
|
+
# h.take(2) # => [[:foo, 0], [:bar, 1]]
|
1418
|
+
#
|
1419
|
+
def take: (Integer n) -> ::Array[Elem]
|
1420
|
+
|
1421
|
+
# <!--
|
1422
|
+
# rdoc-file=enum.c
|
1423
|
+
# - take_while {|element| ... } -> array
|
1424
|
+
# - take_while -> enumerator
|
1425
|
+
# -->
|
1426
|
+
# Calls the block with successive elements as long as the block returns a truthy
|
1427
|
+
# value; returns an array of all elements up to that point:
|
1428
|
+
#
|
1429
|
+
# (1..4).take_while{|i| i < 3 } # => [1, 2]
|
1430
|
+
# h = {foo: 0, bar: 1, baz: 2}
|
1431
|
+
# h.take_while{|element| key, value = *element; value < 2 }
|
1432
|
+
# # => [[:foo, 0], [:bar, 1]]
|
1433
|
+
#
|
1434
|
+
# With no block given, returns an Enumerator.
|
1435
|
+
#
|
1436
|
+
def take_while: () { (Elem) -> boolish } -> ::Array[Elem]
|
1437
|
+
| () -> ::Enumerator[Elem, ::Array[Elem]]
|
1438
|
+
|
1439
|
+
# <!--
|
1440
|
+
# rdoc-file=enum.c
|
1441
|
+
# - to_h(*args) -> hash
|
1442
|
+
# - to_h(*args) {|element| ... } -> hash
|
1443
|
+
# -->
|
1444
|
+
# When `self` consists of 2-element arrays, returns a hash each of whose entries
|
1445
|
+
# is the key-value pair formed from one of those arrays:
|
1446
|
+
#
|
1447
|
+
# [[:foo, 0], [:bar, 1], [:baz, 2]].to_h # => {:foo=>0, :bar=>1, :baz=>2}
|
1448
|
+
#
|
1449
|
+
# When a block is given, the block is called with each element of `self`; the
|
1450
|
+
# block should return a 2-element array which becomes a key-value pair in the
|
1451
|
+
# returned hash:
|
1452
|
+
#
|
1453
|
+
# (0..3).to_h {|i| [i, i ** 2]} # => {0=>0, 1=>1, 2=>4, 3=>9}
|
1454
|
+
#
|
1455
|
+
# Raises an exception if an element of `self` is not a 2-element array, and a
|
1456
|
+
# block is not passed.
|
1457
|
+
#
|
1458
|
+
def to_h: () -> ::Hash[untyped, untyped]
|
1459
|
+
| [T, U] () { (Elem) -> [ T, U ] } -> ::Hash[T, U]
|
1460
|
+
|
1461
|
+
# <!--
|
1462
|
+
# rdoc-file=enum.c
|
1463
|
+
# - each_slice(n) { ... } -> self
|
1464
|
+
# - each_slice(n) -> enumerator
|
1465
|
+
# -->
|
1466
|
+
# Calls the block with each successive disjoint `n`-tuple of elements; returns
|
1467
|
+
# `self`:
|
1468
|
+
#
|
1469
|
+
# a = []
|
1470
|
+
# (1..10).each_slice(3) {|tuple| a.push(tuple) }
|
1471
|
+
# a # => [[1, 2, 3], [4, 5, 6], [7, 8, 9], [10]]
|
1472
|
+
#
|
1473
|
+
# a = []
|
1474
|
+
# h = {foo: 0, bar: 1, baz: 2, bat: 3, bam: 4}
|
1475
|
+
# h.each_slice(2) {|tuple| a.push(tuple) }
|
1476
|
+
# a # => [[[:foo, 0], [:bar, 1]], [[:baz, 2], [:bat, 3]], [[:bam, 4]]]
|
1477
|
+
#
|
1478
|
+
# With no block given, returns an Enumerator.
|
1479
|
+
#
|
1480
|
+
def each_slice: (Integer n) { (::Array[Elem]) -> void } -> self
|
1481
|
+
| (Integer n) -> ::Enumerator[::Array[Elem], self]
|
1482
|
+
|
1483
|
+
interface _NotFound[T]
|
1484
|
+
def call: () -> T
|
1485
|
+
end
|
1486
|
+
|
1487
|
+
# <!--
|
1488
|
+
# rdoc-file=enum.c
|
1489
|
+
# - find(if_none_proc = nil) {|element| ... } -> object or nil
|
1490
|
+
# - find(if_none_proc = nil) -> enumerator
|
1491
|
+
# -->
|
1492
|
+
# Returns the first element for which the block returns a truthy value.
|
1493
|
+
#
|
1494
|
+
# With a block given, calls the block with successive elements of the
|
1495
|
+
# collection; returns the first element for which the block returns a truthy
|
1496
|
+
# value:
|
1497
|
+
#
|
1498
|
+
# (0..9).find {|element| element > 2} # => 3
|
1499
|
+
#
|
1500
|
+
# If no such element is found, calls `if_none_proc` and returns its return
|
1501
|
+
# value.
|
1502
|
+
#
|
1503
|
+
# (0..9).find(proc {false}) {|element| element > 12} # => false
|
1504
|
+
# {foo: 0, bar: 1, baz: 2}.find {|key, value| key.start_with?('b') } # => [:bar, 1]
|
1505
|
+
# {foo: 0, bar: 1, baz: 2}.find(proc {[]}) {|key, value| key.start_with?('c') } # => []
|
1506
|
+
#
|
1507
|
+
# With no block given, returns an Enumerator.
|
1508
|
+
#
|
1509
|
+
def find: () { (Elem) -> boolish } -> Elem?
|
1510
|
+
| () -> ::Enumerator[Elem, Elem?]
|
1511
|
+
| [T] (_NotFound[T] ifnone) { (Elem) -> boolish } -> (Elem | T)
|
1512
|
+
| [T] (_NotFound[T] ifnone) -> ::Enumerator[Elem, Elem | T]
|
1513
|
+
|
1514
|
+
# <!--
|
1515
|
+
# rdoc-file=enum.c
|
1516
|
+
# - flat_map {|element| ... } -> array
|
1517
|
+
# - flat_map -> enumerator
|
1518
|
+
# -->
|
1519
|
+
# Returns an array of flattened objects returned by the block.
|
1520
|
+
#
|
1521
|
+
# With a block given, calls the block with successive elements; returns a
|
1522
|
+
# flattened array of objects returned by the block:
|
1523
|
+
#
|
1524
|
+
# [0, 1, 2, 3].flat_map {|element| -element } # => [0, -1, -2, -3]
|
1525
|
+
# [0, 1, 2, 3].flat_map {|element| [element, -element] } # => [0, 0, 1, -1, 2, -2, 3, -3]
|
1526
|
+
# [[0, 1], [2, 3]].flat_map {|e| e + [100] } # => [0, 1, 100, 2, 3, 100]
|
1527
|
+
# {foo: 0, bar: 1, baz: 2}.flat_map {|key, value| [key, value] } # => [:foo, 0, :bar, 1, :baz, 2]
|
1528
|
+
#
|
1529
|
+
# With no block given, returns an Enumerator.
|
1530
|
+
#
|
1531
|
+
# Alias: #collect_concat.
|
1532
|
+
#
|
1533
|
+
def flat_map: [U] () { (Elem) -> (Array[U] | U) } -> Array[U]
|
1534
|
+
| () -> ::Enumerator[Elem, Array[untyped]]
|
1535
|
+
|
1536
|
+
# <!-- rdoc-file=enum.c -->
|
1537
|
+
# Returns an array of objects returned by the block.
|
1538
|
+
#
|
1539
|
+
# With a block given, calls the block with successive elements; returns an array
|
1540
|
+
# of the objects returned by the block:
|
1541
|
+
#
|
1542
|
+
# (0..4).map {|i| i*i } # => [0, 1, 4, 9, 16]
|
1543
|
+
# {foo: 0, bar: 1, baz: 2}.map {|key, value| value*2} # => [0, 2, 4]
|
1544
|
+
#
|
1545
|
+
# With no block given, returns an Enumerator.
|
1546
|
+
#
|
1547
|
+
def map: [U] () { (Elem arg0) -> U } -> ::Array[U]
|
1548
|
+
| () -> ::Enumerator[Elem, ::Array[untyped]]
|
1549
|
+
|
1550
|
+
# <!--
|
1551
|
+
# rdoc-file=enum.c
|
1552
|
+
# - include?(object) -> true or false
|
1553
|
+
# -->
|
1554
|
+
# Returns whether for any element `object == element`:
|
1555
|
+
#
|
1556
|
+
# (1..4).include?(2) # => true
|
1557
|
+
# (1..4).include?(5) # => false
|
1558
|
+
# (1..4).include?('2') # => false
|
1559
|
+
# %w[a b c d].include?('b') # => true
|
1560
|
+
# %w[a b c d].include?('2') # => false
|
1561
|
+
# {foo: 0, bar: 1, baz: 2}.include?(:foo) # => true
|
1562
|
+
# {foo: 0, bar: 1, baz: 2}.include?('foo') # => false
|
1563
|
+
# {foo: 0, bar: 1, baz: 2}.include?(0) # => false
|
1564
|
+
#
|
1565
|
+
def member?: (Elem arg0) -> bool
|
1566
|
+
|
1567
|
+
# <!-- rdoc-file=enum.c -->
|
1568
|
+
# Returns the result of applying a reducer to an initial value and the first
|
1569
|
+
# element of the Enumerable. It then takes the result and applies the function
|
1570
|
+
# to it and the second element of the collection, and so on. The return value is
|
1571
|
+
# the result returned by the final call to the function.
|
1572
|
+
#
|
1573
|
+
# You can think of
|
1574
|
+
#
|
1575
|
+
# [ a, b, c, d ].inject(i) { |r, v| fn(r, v) }
|
1576
|
+
#
|
1577
|
+
# as being
|
1578
|
+
#
|
1579
|
+
# fn(fn(fn(fn(i, a), b), c), d)
|
1580
|
+
#
|
1581
|
+
# In a way the `inject` function *injects* the function between the elements of
|
1582
|
+
# the enumerable.
|
1583
|
+
#
|
1584
|
+
# `inject` is aliased as `reduce`. You use it when you want to *reduce* a
|
1585
|
+
# collection to a single value.
|
1586
|
+
#
|
1587
|
+
# **The Calling Sequences**
|
1588
|
+
#
|
1589
|
+
# Let's start with the most verbose:
|
1590
|
+
#
|
1591
|
+
# enum.inject(initial_value) do |result, next_value|
|
1592
|
+
# # do something with +result+ and +next_value+
|
1593
|
+
# # the value returned by the block becomes the
|
1594
|
+
# # value passed in to the next iteration
|
1595
|
+
# # as +result+
|
1596
|
+
# end
|
1597
|
+
#
|
1598
|
+
# For example:
|
1599
|
+
#
|
1600
|
+
# product = [ 2, 3, 4 ].inject(1) do |result, next_value|
|
1601
|
+
# result * next_value
|
1602
|
+
# end
|
1603
|
+
# product #=> 24
|
1604
|
+
#
|
1605
|
+
# When this runs, the block is first called with `1` (the initial value) and `2`
|
1606
|
+
# (the first element of the array). The block returns `1*2`, so on the next
|
1607
|
+
# iteration the block is called with `2` (the previous result) and `3`. The
|
1608
|
+
# block returns `6`, and is called one last time with `6` and `4`. The result of
|
1609
|
+
# the block, `24` becomes the value returned by `inject`. This code returns the
|
1610
|
+
# product of the elements in the enumerable.
|
1611
|
+
#
|
1612
|
+
# **First Shortcut: Default Initial value**
|
1613
|
+
#
|
1614
|
+
# In the case of the previous example, the initial value, `1`, wasn't really
|
1615
|
+
# necessary: the calculation of the product of a list of numbers is
|
1616
|
+
# self-contained.
|
1617
|
+
#
|
1618
|
+
# In these circumstances, you can omit the `initial_value` parameter. `inject`
|
1619
|
+
# will then initially call the block with the first element of the collection as
|
1620
|
+
# the `result` parameter and the second element as the `next_value`.
|
1621
|
+
#
|
1622
|
+
# [ 2, 3, 4 ].inject do |result, next_value|
|
1623
|
+
# result * next_value
|
1624
|
+
# end
|
1625
|
+
#
|
1626
|
+
# This shortcut is convenient, but can only be used when the block produces a
|
1627
|
+
# result which can be passed back to it as a first parameter.
|
1628
|
+
#
|
1629
|
+
# Here's an example where that's not the case: it returns a hash where the keys
|
1630
|
+
# are words and the values are the number of occurrences of that word in the
|
1631
|
+
# enumerable.
|
1632
|
+
#
|
1633
|
+
# freqs = File.read("README.md")
|
1634
|
+
# .scan(/\w{2,}/)
|
1635
|
+
# .reduce(Hash.new(0)) do |counts, word|
|
1636
|
+
# counts[word] += 1
|
1637
|
+
# counts
|
1638
|
+
# end
|
1639
|
+
# freqs #=> {"Actions"=>4,
|
1640
|
+
# "Status"=>5,
|
1641
|
+
# "MinGW"=>3,
|
1642
|
+
# "https"=>27,
|
1643
|
+
# "github"=>10,
|
1644
|
+
# "com"=>15, ...
|
1645
|
+
#
|
1646
|
+
# Note that the last line of the block is just the word `counts`. This ensures
|
1647
|
+
# the return value of the block is the result that's being calculated.
|
1648
|
+
#
|
1649
|
+
# **Second Shortcut: a Reducer function**
|
1650
|
+
#
|
1651
|
+
# A *reducer function* is a function that takes a partial result and the next
|
1652
|
+
# value, returning the next partial result. The block that is given to `inject`
|
1653
|
+
# is a reducer.
|
1654
|
+
#
|
1655
|
+
# You can also write a reducer as a function and pass the name of that function
|
1656
|
+
# (as a symbol) to `inject`. However, for this to work, the function
|
1657
|
+
#
|
1658
|
+
# 1. Must be defined on the type of the result value
|
1659
|
+
# 2. Must accept a single parameter, the next value in the collection, and
|
1660
|
+
# 3. Must return an updated result which will also implement the function.
|
1661
|
+
#
|
1662
|
+
# Here's an example that adds elements to a string. The two calls invoke the
|
1663
|
+
# functions String#concat and String#+ on the result so far, passing it the next
|
1664
|
+
# value.
|
1665
|
+
#
|
1666
|
+
# s = [ "cat", " ", "dog" ].inject("", :concat)
|
1667
|
+
# s #=> "cat dog"
|
1668
|
+
# s = [ "cat", " ", "dog" ].inject("The result is:", :+)
|
1669
|
+
# s #=> "The result is: cat dog"
|
1670
|
+
#
|
1671
|
+
# Here's a more complex example when the result object maintains state of a
|
1672
|
+
# different type to the enumerable elements.
|
1673
|
+
#
|
1674
|
+
# class Turtle
|
1675
|
+
#
|
1676
|
+
# def initialize
|
1677
|
+
# @x = @y = 0
|
1678
|
+
# end
|
1679
|
+
#
|
1680
|
+
# def move(dir)
|
1681
|
+
# case dir
|
1682
|
+
# when "n" then @y += 1
|
1683
|
+
# when "s" then @y -= 1
|
1684
|
+
# when "e" then @x += 1
|
1685
|
+
# when "w" then @x -= 1
|
1686
|
+
# end
|
1687
|
+
# self
|
1688
|
+
# end
|
1689
|
+
# end
|
1690
|
+
#
|
1691
|
+
# position = "nnneesw".chars.reduce(Turtle.new, :move)
|
1692
|
+
# position #=>> #<Turtle:0x00000001052f4698 @y=2, @x=1>
|
1693
|
+
#
|
1694
|
+
# **Third Shortcut: Reducer With no Initial Value**
|
1695
|
+
#
|
1696
|
+
# If your reducer returns a value that it can accept as a parameter, then you
|
1697
|
+
# don't have to pass in an initial value. Here `:*` is the name of the *times*
|
1698
|
+
# function:
|
1699
|
+
#
|
1700
|
+
# product = [ 2, 3, 4 ].inject(:*)
|
1701
|
+
# product # => 24
|
1702
|
+
#
|
1703
|
+
# String concatenation again:
|
1704
|
+
#
|
1705
|
+
# s = [ "cat", " ", "dog" ].inject(:+)
|
1706
|
+
# s #=> "cat dog"
|
1707
|
+
#
|
1708
|
+
# And an example that converts a hash to an array of two-element subarrays.
|
1709
|
+
#
|
1710
|
+
# nested = {foo: 0, bar: 1}.inject([], :push)
|
1711
|
+
# nested # => [[:foo, 0], [:bar, 1]]
|
1712
|
+
#
|
1713
|
+
alias reduce inject
|
1714
|
+
|
1715
|
+
# <!--
|
1716
|
+
# rdoc-file=enum.c
|
1717
|
+
# - to_a(*args) -> array
|
1718
|
+
# -->
|
1719
|
+
# Returns an array containing the items in `self`:
|
1720
|
+
#
|
1721
|
+
# (0..4).to_a # => [0, 1, 2, 3, 4]
|
1722
|
+
#
|
1723
|
+
def to_a: () -> ::Array[Elem]
|
1724
|
+
|
1725
|
+
# <!--
|
1726
|
+
# rdoc-file=enumerator.c
|
1727
|
+
# - e.lazy -> lazy_enumerator
|
1728
|
+
# -->
|
1729
|
+
# Returns an Enumerator::Lazy, which redefines most Enumerable methods to
|
1730
|
+
# postpone enumeration and enumerate values only on an as-needed basis.
|
1731
|
+
#
|
1732
|
+
# ### Example
|
1733
|
+
#
|
1734
|
+
# The following program finds pythagorean triples:
|
1735
|
+
#
|
1736
|
+
# def pythagorean_triples
|
1737
|
+
# (1..Float::INFINITY).lazy.flat_map {|z|
|
1738
|
+
# (1..z).flat_map {|x|
|
1739
|
+
# (x..z).select {|y|
|
1740
|
+
# x**2 + y**2 == z**2
|
1741
|
+
# }.map {|y|
|
1742
|
+
# [x, y, z]
|
1743
|
+
# }
|
1744
|
+
# }
|
1745
|
+
# }
|
1746
|
+
# end
|
1747
|
+
# # show first ten pythagorean triples
|
1748
|
+
# p pythagorean_triples.take(10).force # take is lazy, so force is needed
|
1749
|
+
# p pythagorean_triples.first(10) # first is eager
|
1750
|
+
# # show pythagorean triples less than 100
|
1751
|
+
# p pythagorean_triples.take_while { |*, z| z < 100 }.force
|
1752
|
+
#
|
1753
|
+
def lazy: () -> Enumerator::Lazy[Elem]
|
1754
|
+
|
1755
|
+
# <!--
|
1756
|
+
# rdoc-file=enum.c
|
1757
|
+
# - uniq -> array
|
1758
|
+
# - uniq {|element| ... } -> array
|
1759
|
+
# -->
|
1760
|
+
# With no block, returns a new array containing only unique elements; the array
|
1761
|
+
# has no two elements `e0` and `e1` such that `e0.eql?(e1)`:
|
1762
|
+
#
|
1763
|
+
# %w[a b c c b a a b c].uniq # => ["a", "b", "c"]
|
1764
|
+
# [0, 1, 2, 2, 1, 0, 0, 1, 2].uniq # => [0, 1, 2]
|
1765
|
+
#
|
1766
|
+
# With a block, returns a new array containing elements only for which the block
|
1767
|
+
# returns a unique value:
|
1768
|
+
#
|
1769
|
+
# a = [0, 1, 2, 3, 4, 5, 5, 4, 3, 2, 1]
|
1770
|
+
# a.uniq {|i| i.even? ? i : 0 } # => [0, 2, 4]
|
1771
|
+
# a = %w[a b c d e e d c b a a b c d e]
|
1772
|
+
# a.uniq {|c| c < 'c' } # => ["a", "c"]
|
1773
|
+
#
|
1774
|
+
def uniq: () -> ::Array[Elem]
|
1775
|
+
| () { (Elem item) -> untyped } -> ::Array[Elem]
|
1776
|
+
|
1777
|
+
# <!--
|
1778
|
+
# rdoc-file=enum.c
|
1779
|
+
# - sum(initial_value = 0) -> number
|
1780
|
+
# - sum(initial_value = 0) {|element| ... } -> object
|
1781
|
+
# -->
|
1782
|
+
# With no block given, returns the sum of `initial_value` and the elements:
|
1783
|
+
#
|
1784
|
+
# (1..100).sum # => 5050
|
1785
|
+
# (1..100).sum(1) # => 5051
|
1786
|
+
# ('a'..'d').sum('foo') # => "fooabcd"
|
1787
|
+
#
|
1788
|
+
# Generally, the sum is computed using methods `+` and `each`; for performance
|
1789
|
+
# optimizations, those methods may not be used, and so any redefinition of those
|
1790
|
+
# methods may not have effect here.
|
1791
|
+
#
|
1792
|
+
# One such optimization: When possible, computes using Gauss's summation formula
|
1793
|
+
# *n(n+1)/2*:
|
1794
|
+
#
|
1795
|
+
# 100 * (100 + 1) / 2 # => 5050
|
1796
|
+
#
|
1797
|
+
# With a block given, calls the block with each element; returns the sum of
|
1798
|
+
# `initial_value` and the block return values:
|
1799
|
+
#
|
1800
|
+
# (1..4).sum {|i| i*i } # => 30
|
1801
|
+
# (1..4).sum(100) {|i| i*i } # => 130
|
1802
|
+
# h = {a: 0, b: 1, c: 2, d: 3, e: 4, f: 5}
|
1803
|
+
# h.sum {|key, value| value.odd? ? value : 0 } # => 9
|
1804
|
+
# ('a'..'f').sum('x') {|c| c < 'd' ? c : '' } # => "xabc"
|
1805
|
+
#
|
1806
|
+
def sum: () -> (Elem | Integer)
|
1807
|
+
| [T] () { (Elem arg0) -> T } -> (Integer | T)
|
1808
|
+
| [T] (?T arg0) -> (Elem | T)
|
1809
|
+
| [U] (?U arg0) { (Elem arg0) -> U } -> U
|
1810
|
+
|
1811
|
+
# <!--
|
1812
|
+
# rdoc-file=enum.c
|
1813
|
+
# - filter_map {|element| ... } -> array
|
1814
|
+
# - filter_map -> enumerator
|
1815
|
+
# -->
|
1816
|
+
# Returns an array containing truthy elements returned by the block.
|
1817
|
+
#
|
1818
|
+
# With a block given, calls the block with successive elements; returns an array
|
1819
|
+
# containing each truthy value returned by the block:
|
1820
|
+
#
|
1821
|
+
# (0..9).filter_map {|i| i * 2 if i.even? } # => [0, 4, 8, 12, 16]
|
1822
|
+
# {foo: 0, bar: 1, baz: 2}.filter_map {|key, value| key if value.even? } # => [:foo, :baz]
|
1823
|
+
#
|
1824
|
+
# When no block given, returns an Enumerator.
|
1825
|
+
#
|
1826
|
+
def filter_map: [U] () { (Elem elem) -> (nil | false | U) } -> ::Array[U]
|
1827
|
+
| () -> ::Enumerator[Elem, ::Array[untyped]]
|
1828
|
+
|
1829
|
+
# <!--
|
1830
|
+
# rdoc-file=enumerator.c
|
1831
|
+
# - e.chain(*enums) -> enumerator
|
1832
|
+
# -->
|
1833
|
+
# Returns an enumerator object generated from this enumerator and given
|
1834
|
+
# enumerables.
|
1835
|
+
#
|
1836
|
+
# e = (1..3).chain([4, 5])
|
1837
|
+
# e.to_a #=> [1, 2, 3, 4, 5]
|
1838
|
+
#
|
1839
|
+
def chain: [Elem2] (*_Each[Elem2] enumerables) -> ::Enumerator::Chain[Elem | Elem2]
|
1840
|
+
|
1841
|
+
# <!--
|
1842
|
+
# rdoc-file=enum.c
|
1843
|
+
# - tally(hash = {}) -> hash
|
1844
|
+
# -->
|
1845
|
+
# When argument `hash` is not given, returns a new hash whose keys are the
|
1846
|
+
# distinct elements in `self`; each integer value is the count of occurrences of
|
1847
|
+
# each element:
|
1848
|
+
#
|
1849
|
+
# %w[a b c b c a c b].tally # => {"a"=>2, "b"=>3, "c"=>3}
|
1850
|
+
#
|
1851
|
+
# When argument `hash` is given, returns `hash`, possibly augmented; for each
|
1852
|
+
# element `ele` in `self`:
|
1853
|
+
#
|
1854
|
+
# * Adds it as a key with a zero value if that key does not already exist:
|
1855
|
+
#
|
1856
|
+
# hash[ele] = 0 unless hash.include?(ele)
|
1857
|
+
#
|
1858
|
+
# * Increments the value of key `ele`:
|
1859
|
+
#
|
1860
|
+
# hash[ele] += 1
|
1861
|
+
#
|
1862
|
+
# This is useful for accumulating tallies across multiple enumerables:
|
1863
|
+
#
|
1864
|
+
# h = {} # => {}
|
1865
|
+
# %w[a c d b c a].tally(h) # => {"a"=>2, "c"=>2, "d"=>1, "b"=>1}
|
1866
|
+
# %w[b a z].tally(h) # => {"a"=>3, "c"=>2, "d"=>1, "b"=>2, "z"=>1}
|
1867
|
+
# %w[b a m].tally(h) # => {"a"=>4, "c"=>2, "d"=>1, "b"=>3, "z"=>1, "m"=>1}
|
1868
|
+
#
|
1869
|
+
# The key to be added or found for an element depends on the class of `self`;
|
1870
|
+
# see [Enumerable in Ruby
|
1871
|
+
# Classes](rdoc-ref:Enumerable@Enumerable+in+Ruby+Classes).
|
1872
|
+
#
|
1873
|
+
# Examples:
|
1874
|
+
#
|
1875
|
+
# * Array (and certain array-like classes): the key is the element (as above).
|
1876
|
+
# * Hash (and certain hash-like classes): the key is the 2-element array
|
1877
|
+
# formed from the key-value pair:
|
1878
|
+
#
|
1879
|
+
# h = {} # => {}
|
1880
|
+
# {foo: 'a', bar: 'b'}.tally(h) # => {[:foo, "a"]=>1, [:bar, "b"]=>1}
|
1881
|
+
# {foo: 'c', bar: 'd'}.tally(h) # => {[:foo, "a"]=>1, [:bar, "b"]=>1, [:foo, "c"]=>1, [:bar, "d"]=>1}
|
1882
|
+
# {foo: 'a', bar: 'b'}.tally(h) # => {[:foo, "a"]=>2, [:bar, "b"]=>2, [:foo, "c"]=>1, [:bar, "d"]=>1}
|
1883
|
+
# {foo: 'c', bar: 'd'}.tally(h) # => {[:foo, "a"]=>2, [:bar, "b"]=>2, [:foo, "c"]=>2, [:bar, "d"]=>2}
|
1884
|
+
#
|
1885
|
+
def tally: (?Hash[Elem, Integer] hash) -> ::Hash[Elem, Integer]
|
1886
|
+
|
1887
|
+
# <!--
|
1888
|
+
# rdoc-file=enum.c
|
1889
|
+
# - each_entry(*args) {|element| ... } -> self
|
1890
|
+
# - each_entry(*args) -> enumerator
|
1891
|
+
# -->
|
1892
|
+
# Calls the given block with each element, converting multiple values from yield
|
1893
|
+
# to an array; returns `self`:
|
1894
|
+
#
|
1895
|
+
# a = []
|
1896
|
+
# (1..4).each_entry {|element| a.push(element) } # => 1..4
|
1897
|
+
# a # => [1, 2, 3, 4]
|
1898
|
+
#
|
1899
|
+
# a = []
|
1900
|
+
# h = {foo: 0, bar: 1, baz:2}
|
1901
|
+
# h.each_entry {|element| a.push(element) }
|
1902
|
+
# # => {:foo=>0, :bar=>1, :baz=>2}
|
1903
|
+
# a # => [[:foo, 0], [:bar, 1], [:baz, 2]]
|
1904
|
+
#
|
1905
|
+
# class Foo
|
1906
|
+
# include Enumerable
|
1907
|
+
# def each
|
1908
|
+
# yield 1
|
1909
|
+
# yield 1, 2
|
1910
|
+
# yield
|
1911
|
+
# end
|
1912
|
+
# end
|
1913
|
+
# Foo.new.each_entry {|yielded| p yielded }
|
1914
|
+
#
|
1915
|
+
# Output:
|
1916
|
+
#
|
1917
|
+
# 1
|
1918
|
+
# [1, 2]
|
1919
|
+
# nil
|
1920
|
+
#
|
1921
|
+
# With no block given, returns an Enumerator.
|
1922
|
+
#
|
1923
|
+
def each_entry: () -> ::Enumerator[Elem, self]
|
1924
|
+
| () { (Elem arg0) -> untyped } -> self
|
1925
|
+
|
1926
|
+
# <!--
|
1927
|
+
# rdoc-file=enum.c
|
1928
|
+
# - zip(*other_enums) -> array
|
1929
|
+
# - zip(*other_enums) {|array| ... } -> nil
|
1930
|
+
# -->
|
1931
|
+
# With no block given, returns a new array `new_array` of size self.size whose
|
1932
|
+
# elements are arrays. Each nested array `new_array[n]` is of size
|
1933
|
+
# `other_enums.size+1`, and contains:
|
1934
|
+
#
|
1935
|
+
# * The `n`-th element of self.
|
1936
|
+
# * The `n`-th element of each of the `other_enums`.
|
1937
|
+
#
|
1938
|
+
# If all `other_enums` and self are the same size, all elements are included in
|
1939
|
+
# the result, and there is no `nil`-filling:
|
1940
|
+
#
|
1941
|
+
# a = [:a0, :a1, :a2, :a3]
|
1942
|
+
# b = [:b0, :b1, :b2, :b3]
|
1943
|
+
# c = [:c0, :c1, :c2, :c3]
|
1944
|
+
# d = a.zip(b, c)
|
1945
|
+
# d # => [[:a0, :b0, :c0], [:a1, :b1, :c1], [:a2, :b2, :c2], [:a3, :b3, :c3]]
|
1946
|
+
#
|
1947
|
+
# f = {foo: 0, bar: 1, baz: 2}
|
1948
|
+
# g = {goo: 3, gar: 4, gaz: 5}
|
1949
|
+
# h = {hoo: 6, har: 7, haz: 8}
|
1950
|
+
# d = f.zip(g, h)
|
1951
|
+
# d # => [
|
1952
|
+
# # [[:foo, 0], [:goo, 3], [:hoo, 6]],
|
1953
|
+
# # [[:bar, 1], [:gar, 4], [:har, 7]],
|
1954
|
+
# # [[:baz, 2], [:gaz, 5], [:haz, 8]]
|
1955
|
+
# # ]
|
1956
|
+
#
|
1957
|
+
# If any enumerable in other_enums is smaller than self, fills to `self.size`
|
1958
|
+
# with `nil`:
|
1959
|
+
#
|
1960
|
+
# a = [:a0, :a1, :a2, :a3]
|
1961
|
+
# b = [:b0, :b1, :b2]
|
1962
|
+
# c = [:c0, :c1]
|
1963
|
+
# d = a.zip(b, c)
|
1964
|
+
# d # => [[:a0, :b0, :c0], [:a1, :b1, :c1], [:a2, :b2, nil], [:a3, nil, nil]]
|
1965
|
+
#
|
1966
|
+
# If any enumerable in other_enums is larger than self, its trailing elements
|
1967
|
+
# are ignored:
|
1968
|
+
#
|
1969
|
+
# a = [:a0, :a1, :a2, :a3]
|
1970
|
+
# b = [:b0, :b1, :b2, :b3, :b4]
|
1971
|
+
# c = [:c0, :c1, :c2, :c3, :c4, :c5]
|
1972
|
+
# d = a.zip(b, c)
|
1973
|
+
# d # => [[:a0, :b0, :c0], [:a1, :b1, :c1], [:a2, :b2, :c2], [:a3, :b3, :c3]]
|
1974
|
+
#
|
1975
|
+
# When a block is given, calls the block with each of the sub-arrays (formed as
|
1976
|
+
# above); returns nil:
|
1977
|
+
#
|
1978
|
+
# a = [:a0, :a1, :a2, :a3]
|
1979
|
+
# b = [:b0, :b1, :b2, :b3]
|
1980
|
+
# c = [:c0, :c1, :c2, :c3]
|
1981
|
+
# a.zip(b, c) {|sub_array| p sub_array} # => nil
|
1982
|
+
#
|
1983
|
+
# Output:
|
1984
|
+
#
|
1985
|
+
# [:a0, :b0, :c0]
|
1986
|
+
# [:a1, :b1, :c1]
|
1987
|
+
# [:a2, :b2, :c2]
|
1988
|
+
# [:a3, :b3, :c3]
|
1989
|
+
#
|
1990
|
+
def zip: [Elem2] (_Each[Elem2] enum) -> Array[[ Elem, Elem2? ]]
|
1991
|
+
| (_Each[untyped], *_Each[untyped]) -> Array[Array[untyped]]
|
1992
|
+
| [Elem2] (_Each[Elem2]) { ([ Elem, Elem2? ]) -> void } -> nil
|
1993
|
+
| (_Each[untyped], *_Each[untyped]) { (Array[untyped]) -> void } -> nil
|
1994
|
+
|
1995
|
+
# <!--
|
1996
|
+
# rdoc-file=enum.c
|
1997
|
+
# - chunk {|array| ... } -> enumerator
|
1998
|
+
# -->
|
1999
|
+
# Each element in the returned enumerator is a 2-element array consisting of:
|
2000
|
+
#
|
2001
|
+
# * A value returned by the block.
|
2002
|
+
# * An array ("chunk") containing the element for which that value was
|
2003
|
+
# returned, and all following elements for which the block returned the same
|
2004
|
+
# value:
|
2005
|
+
#
|
2006
|
+
# So that:
|
2007
|
+
#
|
2008
|
+
# * Each block return value that is different from its predecessor begins a
|
2009
|
+
# new chunk.
|
2010
|
+
# * Each block return value that is the same as its predecessor continues the
|
2011
|
+
# same chunk.
|
2012
|
+
#
|
2013
|
+
# Example:
|
2014
|
+
#
|
2015
|
+
# e = (0..10).chunk {|i| (i / 3).floor } # => #<Enumerator: ...>
|
2016
|
+
# # The enumerator elements.
|
2017
|
+
# e.next # => [0, [0, 1, 2]]
|
2018
|
+
# e.next # => [1, [3, 4, 5]]
|
2019
|
+
# e.next # => [2, [6, 7, 8]]
|
2020
|
+
# e.next # => [3, [9, 10]]
|
2021
|
+
#
|
2022
|
+
# Method `chunk` is especially useful for an enumerable that is already sorted.
|
2023
|
+
# This example counts words for each initial letter in a large array of words:
|
2024
|
+
#
|
2025
|
+
# # Get sorted words from a web page.
|
2026
|
+
# url = 'https://raw.githubusercontent.com/eneko/data-repository/master/data/words.txt'
|
2027
|
+
# words = URI::open(url).readlines
|
2028
|
+
# # Make chunks, one for each letter.
|
2029
|
+
# e = words.chunk {|word| word.upcase[0] } # => #<Enumerator: ...>
|
2030
|
+
# # Display 'A' through 'F'.
|
2031
|
+
# e.each {|c, words| p [c, words.length]; break if c == 'F' }
|
2032
|
+
#
|
2033
|
+
# Output:
|
2034
|
+
#
|
2035
|
+
# ["A", 17096]
|
2036
|
+
# ["B", 11070]
|
2037
|
+
# ["C", 19901]
|
2038
|
+
# ["D", 10896]
|
2039
|
+
# ["E", 8736]
|
2040
|
+
# ["F", 6860]
|
2041
|
+
#
|
2042
|
+
# You can use the special symbol `:_alone` to force an element into its own
|
2043
|
+
# separate chuck:
|
2044
|
+
#
|
2045
|
+
# a = [0, 0, 1, 1]
|
2046
|
+
# e = a.chunk{|i| i.even? ? :_alone : true }
|
2047
|
+
# e.to_a # => [[:_alone, [0]], [:_alone, [0]], [true, [1, 1]]]
|
2048
|
+
#
|
2049
|
+
# For example, you can put each line that contains a URL into its own chunk:
|
2050
|
+
#
|
2051
|
+
# pattern = /http/
|
2052
|
+
# open(filename) { |f|
|
2053
|
+
# f.chunk { |line| line =~ pattern ? :_alone : true }.each { |key, lines|
|
2054
|
+
# pp lines
|
2055
|
+
# }
|
2056
|
+
# }
|
2057
|
+
#
|
2058
|
+
# You can use the special symbol `:_separator` or `nil` to force an element to
|
2059
|
+
# be ignored (not included in any chunk):
|
2060
|
+
#
|
2061
|
+
# a = [0, 0, -1, 1, 1]
|
2062
|
+
# e = a.chunk{|i| i < 0 ? :_separator : true }
|
2063
|
+
# e.to_a # => [[true, [0, 0]], [true, [1, 1]]]
|
2064
|
+
#
|
2065
|
+
# Note that the separator does end the chunk:
|
2066
|
+
#
|
2067
|
+
# a = [0, 0, -1, 1, -1, 1]
|
2068
|
+
# e = a.chunk{|i| i < 0 ? :_separator : true }
|
2069
|
+
# e.to_a # => [[true, [0, 0]], [true, [1]], [true, [1]]]
|
2070
|
+
#
|
2071
|
+
# For example, the sequence of hyphens in svn log can be eliminated as follows:
|
2072
|
+
#
|
2073
|
+
# sep = "-"*72 + "\n"
|
2074
|
+
# IO.popen("svn log README") { |f|
|
2075
|
+
# f.chunk { |line|
|
2076
|
+
# line != sep || nil
|
2077
|
+
# }.each { |_, lines|
|
2078
|
+
# pp lines
|
2079
|
+
# }
|
2080
|
+
# }
|
2081
|
+
# #=> ["r20018 | knu | 2008-10-29 13:20:42 +0900 (Wed, 29 Oct 2008) | 2 lines\n",
|
2082
|
+
# # "\n",
|
2083
|
+
# # "* README, README.ja: Update the portability section.\n",
|
2084
|
+
# # "\n"]
|
2085
|
+
# # ["r16725 | knu | 2008-05-31 23:34:23 +0900 (Sat, 31 May 2008) | 2 lines\n",
|
2086
|
+
# # "\n",
|
2087
|
+
# # "* README, README.ja: Add a note about default C flags.\n",
|
2088
|
+
# # "\n"]
|
2089
|
+
# # ...
|
2090
|
+
#
|
2091
|
+
# Paragraphs separated by empty lines can be parsed as follows:
|
2092
|
+
#
|
2093
|
+
# File.foreach("README").chunk { |line|
|
2094
|
+
# /\A\s*\z/ !~ line || nil
|
2095
|
+
# }.each { |_, lines|
|
2096
|
+
# pp lines
|
2097
|
+
# }
|
2098
|
+
#
|
2099
|
+
def chunk: [U] () { (Elem elt) -> U } -> ::Enumerator[[ U, ::Array[Elem] ]]
|
2100
|
+
| () -> ::Enumerator[Elem, ::Enumerator[[ untyped, ::Array[Elem] ]]]
|
2101
|
+
|
2102
|
+
# <!--
|
2103
|
+
# rdoc-file=enum.c
|
2104
|
+
# - enum.chunk_while {|elt_before, elt_after| bool } -> an_enumerator
|
2105
|
+
# -->
|
2106
|
+
# Creates an enumerator for each chunked elements. The beginnings of chunks are
|
2107
|
+
# defined by the block.
|
2108
|
+
#
|
2109
|
+
# This method splits each chunk using adjacent elements, *elt_before* and
|
2110
|
+
# *elt_after*, in the receiver enumerator. This method split chunks between
|
2111
|
+
# *elt_before* and *elt_after* where the block returns `false`.
|
2112
|
+
#
|
2113
|
+
# The block is called the length of the receiver enumerator minus one.
|
2114
|
+
#
|
2115
|
+
# The result enumerator yields the chunked elements as an array. So `each`
|
2116
|
+
# method can be called as follows:
|
2117
|
+
#
|
2118
|
+
# enum.chunk_while { |elt_before, elt_after| bool }.each { |ary| ... }
|
2119
|
+
#
|
2120
|
+
# Other methods of the Enumerator class and Enumerable module, such as `to_a`,
|
2121
|
+
# `map`, etc., are also usable.
|
2122
|
+
#
|
2123
|
+
# For example, one-by-one increasing subsequence can be chunked as follows:
|
2124
|
+
#
|
2125
|
+
# a = [1,2,4,9,10,11,12,15,16,19,20,21]
|
2126
|
+
# b = a.chunk_while {|i, j| i+1 == j }
|
2127
|
+
# p b.to_a #=> [[1, 2], [4], [9, 10, 11, 12], [15, 16], [19, 20, 21]]
|
2128
|
+
# c = b.map {|a| a.length < 3 ? a : "#{a.first}-#{a.last}" }
|
2129
|
+
# p c #=> [[1, 2], [4], "9-12", [15, 16], "19-21"]
|
2130
|
+
# d = c.join(",")
|
2131
|
+
# p d #=> "1,2,4,9-12,15,16,19-21"
|
2132
|
+
#
|
2133
|
+
# Increasing (non-decreasing) subsequence can be chunked as follows:
|
2134
|
+
#
|
2135
|
+
# a = [0, 9, 2, 2, 3, 2, 7, 5, 9, 5]
|
2136
|
+
# p a.chunk_while {|i, j| i <= j }.to_a
|
2137
|
+
# #=> [[0, 9], [2, 2, 3], [2, 7], [5, 9], [5]]
|
2138
|
+
#
|
2139
|
+
# Adjacent evens and odds can be chunked as follows: (Enumerable#chunk is
|
2140
|
+
# another way to do it.)
|
2141
|
+
#
|
2142
|
+
# a = [7, 5, 9, 2, 0, 7, 9, 4, 2, 0]
|
2143
|
+
# p a.chunk_while {|i, j| i.even? == j.even? }.to_a
|
2144
|
+
# #=> [[7, 5, 9], [2, 0], [7, 9], [4, 2, 0]]
|
2145
|
+
#
|
2146
|
+
# Enumerable#slice_when does the same, except splitting when the block returns
|
2147
|
+
# `true` instead of `false`.
|
2148
|
+
#
|
2149
|
+
def chunk_while: () { (Elem elt_before, Elem elt_after) -> boolish } -> ::Enumerator[::Array[Elem]]
|
2150
|
+
|
2151
|
+
# <!--
|
2152
|
+
# rdoc-file=enum.c
|
2153
|
+
# - enum.slice_when {|elt_before, elt_after| bool } -> an_enumerator
|
2154
|
+
# -->
|
2155
|
+
# Creates an enumerator for each chunked elements. The beginnings of chunks are
|
2156
|
+
# defined by the block.
|
2157
|
+
#
|
2158
|
+
# This method splits each chunk using adjacent elements, *elt_before* and
|
2159
|
+
# *elt_after*, in the receiver enumerator. This method split chunks between
|
2160
|
+
# *elt_before* and *elt_after* where the block returns `true`.
|
2161
|
+
#
|
2162
|
+
# The block is called the length of the receiver enumerator minus one.
|
2163
|
+
#
|
2164
|
+
# The result enumerator yields the chunked elements as an array. So `each`
|
2165
|
+
# method can be called as follows:
|
2166
|
+
#
|
2167
|
+
# enum.slice_when { |elt_before, elt_after| bool }.each { |ary| ... }
|
2168
|
+
#
|
2169
|
+
# Other methods of the Enumerator class and Enumerable module, such as `to_a`,
|
2170
|
+
# `map`, etc., are also usable.
|
2171
|
+
#
|
2172
|
+
# For example, one-by-one increasing subsequence can be chunked as follows:
|
2173
|
+
#
|
2174
|
+
# a = [1,2,4,9,10,11,12,15,16,19,20,21]
|
2175
|
+
# b = a.slice_when {|i, j| i+1 != j }
|
2176
|
+
# p b.to_a #=> [[1, 2], [4], [9, 10, 11, 12], [15, 16], [19, 20, 21]]
|
2177
|
+
# c = b.map {|a| a.length < 3 ? a : "#{a.first}-#{a.last}" }
|
2178
|
+
# p c #=> [[1, 2], [4], "9-12", [15, 16], "19-21"]
|
2179
|
+
# d = c.join(",")
|
2180
|
+
# p d #=> "1,2,4,9-12,15,16,19-21"
|
2181
|
+
#
|
2182
|
+
# Near elements (threshold: 6) in sorted array can be chunked as follows:
|
2183
|
+
#
|
2184
|
+
# a = [3, 11, 14, 25, 28, 29, 29, 41, 55, 57]
|
2185
|
+
# p a.slice_when {|i, j| 6 < j - i }.to_a
|
2186
|
+
# #=> [[3], [11, 14], [25, 28, 29, 29], [41], [55, 57]]
|
2187
|
+
#
|
2188
|
+
# Increasing (non-decreasing) subsequence can be chunked as follows:
|
2189
|
+
#
|
2190
|
+
# a = [0, 9, 2, 2, 3, 2, 7, 5, 9, 5]
|
2191
|
+
# p a.slice_when {|i, j| i > j }.to_a
|
2192
|
+
# #=> [[0, 9], [2, 2, 3], [2, 7], [5, 9], [5]]
|
2193
|
+
#
|
2194
|
+
# Adjacent evens and odds can be chunked as follows: (Enumerable#chunk is
|
2195
|
+
# another way to do it.)
|
2196
|
+
#
|
2197
|
+
# a = [7, 5, 9, 2, 0, 7, 9, 4, 2, 0]
|
2198
|
+
# p a.slice_when {|i, j| i.even? != j.even? }.to_a
|
2199
|
+
# #=> [[7, 5, 9], [2, 0], [7, 9], [4, 2, 0]]
|
2200
|
+
#
|
2201
|
+
# Paragraphs (non-empty lines with trailing empty lines) can be chunked as
|
2202
|
+
# follows: (See Enumerable#chunk to ignore empty lines.)
|
2203
|
+
#
|
2204
|
+
# lines = ["foo\n", "bar\n", "\n", "baz\n", "qux\n"]
|
2205
|
+
# p lines.slice_when {|l1, l2| /\A\s*\z/ =~ l1 && /\S/ =~ l2 }.to_a
|
2206
|
+
# #=> [["foo\n", "bar\n", "\n"], ["baz\n", "qux\n"]]
|
2207
|
+
#
|
2208
|
+
# Enumerable#chunk_while does the same, except splitting when the block returns
|
2209
|
+
# `false` instead of `true`.
|
2210
|
+
#
|
2211
|
+
def slice_when: () { (Elem elt_before, Elem elt_after) -> boolish } -> ::Enumerator[::Array[Elem]]
|
2212
|
+
|
2213
|
+
# <!--
|
2214
|
+
# rdoc-file=enum.c
|
2215
|
+
# - enum.slice_after(pattern) -> an_enumerator
|
2216
|
+
# - enum.slice_after { |elt| bool } -> an_enumerator
|
2217
|
+
# -->
|
2218
|
+
# Creates an enumerator for each chunked elements. The ends of chunks are
|
2219
|
+
# defined by *pattern* and the block.
|
2220
|
+
#
|
2221
|
+
# If *`pattern* === *elt`* returns `true` or the block returns `true` for the
|
2222
|
+
# element, the element is end of a chunk.
|
2223
|
+
#
|
2224
|
+
# The `===` and *block* is called from the first element to the last element of
|
2225
|
+
# *enum*.
|
2226
|
+
#
|
2227
|
+
# The result enumerator yields the chunked elements as an array. So `each`
|
2228
|
+
# method can be called as follows:
|
2229
|
+
#
|
2230
|
+
# enum.slice_after(pattern).each { |ary| ... }
|
2231
|
+
# enum.slice_after { |elt| bool }.each { |ary| ... }
|
2232
|
+
#
|
2233
|
+
# Other methods of the Enumerator class and Enumerable module, such as `map`,
|
2234
|
+
# etc., are also usable.
|
2235
|
+
#
|
2236
|
+
# For example, continuation lines (lines end with backslash) can be concatenated
|
2237
|
+
# as follows:
|
2238
|
+
#
|
2239
|
+
# lines = ["foo\n", "bar\\\n", "baz\n", "\n", "qux\n"]
|
2240
|
+
# e = lines.slice_after(/(?<!\\)\n\z/)
|
2241
|
+
# p e.to_a
|
2242
|
+
# #=> [["foo\n"], ["bar\\\n", "baz\n"], ["\n"], ["qux\n"]]
|
2243
|
+
# p e.map {|ll| ll[0...-1].map {|l| l.sub(/\\\n\z/, "") }.join + ll.last }
|
2244
|
+
# #=>["foo\n", "barbaz\n", "\n", "qux\n"]
|
2245
|
+
#
|
2246
|
+
def slice_after: (untyped pattern) -> ::Enumerator[::Array[Elem]]
|
2247
|
+
| () { (Elem elt) -> boolish } -> ::Enumerator[::Array[Elem]]
|
2248
|
+
|
2249
|
+
# <!--
|
2250
|
+
# rdoc-file=enum.c
|
2251
|
+
# - slice_before(pattern) -> enumerator
|
2252
|
+
# - slice_before {|elt| ... } -> enumerator
|
2253
|
+
# -->
|
2254
|
+
# With argument `pattern`, returns an enumerator that uses the pattern to
|
2255
|
+
# partition elements into arrays ("slices"). An element begins a new slice if
|
2256
|
+
# `element === pattern` (or if it is the first element).
|
2257
|
+
#
|
2258
|
+
# a = %w[foo bar fop for baz fob fog bam foy]
|
2259
|
+
# e = a.slice_before(/ba/) # => #<Enumerator: ...>
|
2260
|
+
# e.each {|array| p array }
|
2261
|
+
#
|
2262
|
+
# Output:
|
2263
|
+
#
|
2264
|
+
# ["foo"]
|
2265
|
+
# ["bar", "fop", "for"]
|
2266
|
+
# ["baz", "fob", "fog"]
|
2267
|
+
# ["bam", "foy"]
|
2268
|
+
#
|
2269
|
+
# With a block, returns an enumerator that uses the block to partition elements
|
2270
|
+
# into arrays. An element begins a new slice if its block return is a truthy
|
2271
|
+
# value (or if it is the first element):
|
2272
|
+
#
|
2273
|
+
# e = (1..20).slice_before {|i| i % 4 == 2 } # => #<Enumerator: ...>
|
2274
|
+
# e.each {|array| p array }
|
2275
|
+
#
|
2276
|
+
# Output:
|
2277
|
+
#
|
2278
|
+
# [1]
|
2279
|
+
# [2, 3, 4, 5]
|
2280
|
+
# [6, 7, 8, 9]
|
2281
|
+
# [10, 11, 12, 13]
|
2282
|
+
# [14, 15, 16, 17]
|
2283
|
+
# [18, 19, 20]
|
2284
|
+
#
|
2285
|
+
# Other methods of the Enumerator class and Enumerable module, such as `to_a`,
|
2286
|
+
# `map`, etc., are also usable.
|
2287
|
+
#
|
2288
|
+
# For example, iteration over ChangeLog entries can be implemented as follows:
|
2289
|
+
#
|
2290
|
+
# # iterate over ChangeLog entries.
|
2291
|
+
# open("ChangeLog") { |f|
|
2292
|
+
# f.slice_before(/\A\S/).each { |e| pp e }
|
2293
|
+
# }
|
2294
|
+
#
|
2295
|
+
# # same as above. block is used instead of pattern argument.
|
2296
|
+
# open("ChangeLog") { |f|
|
2297
|
+
# f.slice_before { |line| /\A\S/ === line }.each { |e| pp e }
|
2298
|
+
# }
|
2299
|
+
#
|
2300
|
+
# "svn proplist -R" produces multiline output for each file. They can be chunked
|
2301
|
+
# as follows:
|
2302
|
+
#
|
2303
|
+
# IO.popen([{"LC_ALL"=>"C"}, "svn", "proplist", "-R"]) { |f|
|
2304
|
+
# f.lines.slice_before(/\AProp/).each { |lines| p lines }
|
2305
|
+
# }
|
2306
|
+
# #=> ["Properties on '.':\n", " svn:ignore\n", " svk:merge\n"]
|
2307
|
+
# # ["Properties on 'goruby.c':\n", " svn:eol-style\n"]
|
2308
|
+
# # ["Properties on 'complex.c':\n", " svn:mime-type\n", " svn:eol-style\n"]
|
2309
|
+
# # ["Properties on 'regparse.c':\n", " svn:eol-style\n"]
|
2310
|
+
# # ...
|
2311
|
+
#
|
2312
|
+
# If the block needs to maintain state over multiple elements, local variables
|
2313
|
+
# can be used. For example, three or more consecutive increasing numbers can be
|
2314
|
+
# squashed as follows (see `chunk_while` for a better way):
|
2315
|
+
#
|
2316
|
+
# a = [0, 2, 3, 4, 6, 7, 9]
|
2317
|
+
# prev = a[0]
|
2318
|
+
# p a.slice_before { |e|
|
2319
|
+
# prev, prev2 = e, prev
|
2320
|
+
# prev2 + 1 != e
|
2321
|
+
# }.map { |es|
|
2322
|
+
# es.length <= 2 ? es.join(",") : "#{es.first}-#{es.last}"
|
2323
|
+
# }.join(",")
|
2324
|
+
# #=> "0,2-4,6,7,9"
|
2325
|
+
#
|
2326
|
+
# However local variables should be used carefully if the result enumerator is
|
2327
|
+
# enumerated twice or more. The local variables should be initialized for each
|
2328
|
+
# enumeration. Enumerator.new can be used to do it.
|
2329
|
+
#
|
2330
|
+
# # Word wrapping. This assumes all characters have same width.
|
2331
|
+
# def wordwrap(words, maxwidth)
|
2332
|
+
# Enumerator.new {|y|
|
2333
|
+
# # cols is initialized in Enumerator.new.
|
2334
|
+
# cols = 0
|
2335
|
+
# words.slice_before { |w|
|
2336
|
+
# cols += 1 if cols != 0
|
2337
|
+
# cols += w.length
|
2338
|
+
# if maxwidth < cols
|
2339
|
+
# cols = w.length
|
2340
|
+
# true
|
2341
|
+
# else
|
2342
|
+
# false
|
2343
|
+
# end
|
2344
|
+
# }.each {|ws| y.yield ws }
|
2345
|
+
# }
|
2346
|
+
# end
|
2347
|
+
# text = (1..20).to_a.join(" ")
|
2348
|
+
# enum = wordwrap(text.split(/\s+/), 10)
|
2349
|
+
# puts "-"*10
|
2350
|
+
# enum.each { |ws| puts ws.join(" ") } # first enumeration.
|
2351
|
+
# puts "-"*10
|
2352
|
+
# enum.each { |ws| puts ws.join(" ") } # second enumeration generates same result as the first.
|
2353
|
+
# puts "-"*10
|
2354
|
+
# #=> ----------
|
2355
|
+
# # 1 2 3 4 5
|
2356
|
+
# # 6 7 8 9 10
|
2357
|
+
# # 11 12 13
|
2358
|
+
# # 14 15 16
|
2359
|
+
# # 17 18 19
|
2360
|
+
# # 20
|
2361
|
+
# # ----------
|
2362
|
+
# # 1 2 3 4 5
|
2363
|
+
# # 6 7 8 9 10
|
2364
|
+
# # 11 12 13
|
2365
|
+
# # 14 15 16
|
2366
|
+
# # 17 18 19
|
2367
|
+
# # 20
|
2368
|
+
# # ----------
|
2369
|
+
#
|
2370
|
+
# mbox contains series of mails which start with Unix From line. So each mail
|
2371
|
+
# can be extracted by slice before Unix From line.
|
2372
|
+
#
|
2373
|
+
# # parse mbox
|
2374
|
+
# open("mbox") { |f|
|
2375
|
+
# f.slice_before { |line|
|
2376
|
+
# line.start_with? "From "
|
2377
|
+
# }.each { |mail|
|
2378
|
+
# unix_from = mail.shift
|
2379
|
+
# i = mail.index("\n")
|
2380
|
+
# header = mail[0...i]
|
2381
|
+
# body = mail[(i+1)..-1]
|
2382
|
+
# body.pop if body.last == "\n"
|
2383
|
+
# fields = header.slice_before { |line| !" \t".include?(line[0]) }.to_a
|
2384
|
+
# p unix_from
|
2385
|
+
# pp fields
|
2386
|
+
# pp body
|
2387
|
+
# }
|
2388
|
+
# }
|
2389
|
+
#
|
2390
|
+
# # split mails in mbox (slice before Unix From line after an empty line)
|
2391
|
+
# open("mbox") { |f|
|
2392
|
+
# emp = true
|
2393
|
+
# f.slice_before { |line|
|
2394
|
+
# prevemp = emp
|
2395
|
+
# emp = line == "\n"
|
2396
|
+
# prevemp && line.start_with?("From ")
|
2397
|
+
# }.each { |mail|
|
2398
|
+
# mail.pop if mail.last == "\n"
|
2399
|
+
# pp mail
|
2400
|
+
# }
|
2401
|
+
# }
|
2402
|
+
#
|
2403
|
+
def slice_before: (untyped pattern) -> ::Enumerator[::Array[Elem]]
|
2404
|
+
| () { (Elem elt) -> boolish } -> ::Enumerator[::Array[Elem]]
|
2405
|
+
end
|