598 haveNextNextGaussian = true; |
498 haveNextNextGaussian = true; |
599 return v1 * multiplier; |
499 return v1 * multiplier; |
600 } |
500 } |
601 } |
501 } |
602 |
502 |
603 // stream methods, coded in a way intended to better isolate for |
|
604 // maintenance purposes the small differences across forms. |
|
605 |
|
606 /** |
|
607 * Returns a stream producing the given {@code streamSize} number of |
|
608 * pseudorandom {@code int} values. |
|
609 * |
|
610 * <p>A pseudorandom {@code int} value is generated as if it's the result of |
|
611 * calling the method {@link #nextInt()}. |
|
612 * |
|
613 * @param streamSize the number of values to generate |
|
614 * @return a stream of pseudorandom {@code int} values |
|
615 * @throws IllegalArgumentException if {@code streamSize} is |
|
616 * less than zero |
|
617 * @since 1.8 |
|
618 */ |
|
619 public IntStream ints(long streamSize) { |
|
620 if (streamSize < 0L) |
|
621 throw new IllegalArgumentException(BadSize); |
|
622 return StreamSupport.intStream |
|
623 (new RandomIntsSpliterator |
|
624 (this, 0L, streamSize, Integer.MAX_VALUE, 0), |
|
625 false); |
|
626 } |
|
627 |
|
628 /** |
|
629 * Returns an effectively unlimited stream of pseudorandom {@code int} |
|
630 * values. |
|
631 * |
|
632 * <p>A pseudorandom {@code int} value is generated as if it's the result of |
|
633 * calling the method {@link #nextInt()}. |
|
634 * |
|
635 * @implNote This method is implemented to be equivalent to {@code |
|
636 * ints(Long.MAX_VALUE)}. |
|
637 * |
|
638 * @return a stream of pseudorandom {@code int} values |
|
639 * @since 1.8 |
|
640 */ |
|
641 public IntStream ints() { |
|
642 return StreamSupport.intStream |
|
643 (new RandomIntsSpliterator |
|
644 (this, 0L, Long.MAX_VALUE, Integer.MAX_VALUE, 0), |
|
645 false); |
|
646 } |
|
647 |
|
648 /** |
|
649 * Returns a stream producing the given {@code streamSize} number |
|
650 * of pseudorandom {@code int} values, each conforming to the given |
|
651 * origin (inclusive) and bound (exclusive). |
|
652 * |
|
653 * <p>A pseudorandom {@code int} value is generated as if it's the result of |
|
654 * calling the following method with the origin and bound: |
|
655 * <pre> {@code |
|
656 * int nextInt(int origin, int bound) { |
|
657 * int n = bound - origin; |
|
658 * if (n > 0) { |
|
659 * return nextInt(n) + origin; |
|
660 * } |
|
661 * else { // range not representable as int |
|
662 * int r; |
|
663 * do { |
|
664 * r = nextInt(); |
|
665 * } while (r < origin || r >= bound); |
|
666 * return r; |
|
667 * } |
|
668 * }}</pre> |
|
669 * |
|
670 * @param streamSize the number of values to generate |
|
671 * @param randomNumberOrigin the origin (inclusive) of each random value |
|
672 * @param randomNumberBound the bound (exclusive) of each random value |
|
673 * @return a stream of pseudorandom {@code int} values, |
|
674 * each with the given origin (inclusive) and bound (exclusive) |
|
675 * @throws IllegalArgumentException if {@code streamSize} is |
|
676 * less than zero, or {@code randomNumberOrigin} |
|
677 * is greater than or equal to {@code randomNumberBound} |
|
678 * @since 1.8 |
|
679 */ |
|
680 public IntStream ints(long streamSize, int randomNumberOrigin, |
|
681 int randomNumberBound) { |
|
682 if (streamSize < 0L) |
|
683 throw new IllegalArgumentException(BadSize); |
|
684 if (randomNumberOrigin >= randomNumberBound) |
|
685 throw new IllegalArgumentException(BadRange); |
|
686 return StreamSupport.intStream |
|
687 (new RandomIntsSpliterator |
|
688 (this, 0L, streamSize, randomNumberOrigin, randomNumberBound), |
|
689 false); |
|
690 } |
|
691 |
|
692 /** |
|
693 * Returns an effectively unlimited stream of pseudorandom {@code |
|
694 * int} values, each conforming to the given origin (inclusive) and bound |
|
695 * (exclusive). |
|
696 * |
|
697 * <p>A pseudorandom {@code int} value is generated as if it's the result of |
|
698 * calling the following method with the origin and bound: |
|
699 * <pre> {@code |
|
700 * int nextInt(int origin, int bound) { |
|
701 * int n = bound - origin; |
|
702 * if (n > 0) { |
|
703 * return nextInt(n) + origin; |
|
704 * } |
|
705 * else { // range not representable as int |
|
706 * int r; |
|
707 * do { |
|
708 * r = nextInt(); |
|
709 * } while (r < origin || r >= bound); |
|
710 * return r; |
|
711 * } |
|
712 * }}</pre> |
|
713 * |
|
714 * @implNote This method is implemented to be equivalent to {@code |
|
715 * ints(Long.MAX_VALUE, randomNumberOrigin, randomNumberBound)}. |
|
716 * |
|
717 * @param randomNumberOrigin the origin (inclusive) of each random value |
|
718 * @param randomNumberBound the bound (exclusive) of each random value |
|
719 * @return a stream of pseudorandom {@code int} values, |
|
720 * each with the given origin (inclusive) and bound (exclusive) |
|
721 * @throws IllegalArgumentException if {@code randomNumberOrigin} |
|
722 * is greater than or equal to {@code randomNumberBound} |
|
723 * @since 1.8 |
|
724 */ |
|
725 public IntStream ints(int randomNumberOrigin, int randomNumberBound) { |
|
726 if (randomNumberOrigin >= randomNumberBound) |
|
727 throw new IllegalArgumentException(BadRange); |
|
728 return StreamSupport.intStream |
|
729 (new RandomIntsSpliterator |
|
730 (this, 0L, Long.MAX_VALUE, randomNumberOrigin, randomNumberBound), |
|
731 false); |
|
732 } |
|
733 |
|
734 /** |
|
735 * Returns a stream producing the given {@code streamSize} number of |
|
736 * pseudorandom {@code long} values. |
|
737 * |
|
738 * <p>A pseudorandom {@code long} value is generated as if it's the result |
|
739 * of calling the method {@link #nextLong()}. |
|
740 * |
|
741 * @param streamSize the number of values to generate |
|
742 * @return a stream of pseudorandom {@code long} values |
|
743 * @throws IllegalArgumentException if {@code streamSize} is |
|
744 * less than zero |
|
745 * @since 1.8 |
|
746 */ |
|
747 public LongStream longs(long streamSize) { |
|
748 if (streamSize < 0L) |
|
749 throw new IllegalArgumentException(BadSize); |
|
750 return StreamSupport.longStream |
|
751 (new RandomLongsSpliterator |
|
752 (this, 0L, streamSize, Long.MAX_VALUE, 0L), |
|
753 false); |
|
754 } |
|
755 |
|
756 /** |
|
757 * Returns an effectively unlimited stream of pseudorandom {@code long} |
|
758 * values. |
|
759 * |
|
760 * <p>A pseudorandom {@code long} value is generated as if it's the result |
|
761 * of calling the method {@link #nextLong()}. |
|
762 * |
|
763 * @implNote This method is implemented to be equivalent to {@code |
|
764 * longs(Long.MAX_VALUE)}. |
|
765 * |
|
766 * @return a stream of pseudorandom {@code long} values |
|
767 * @since 1.8 |
|
768 */ |
|
769 public LongStream longs() { |
|
770 return StreamSupport.longStream |
|
771 (new RandomLongsSpliterator |
|
772 (this, 0L, Long.MAX_VALUE, Long.MAX_VALUE, 0L), |
|
773 false); |
|
774 } |
|
775 |
|
776 /** |
|
777 * Returns a stream producing the given {@code streamSize} number of |
|
778 * pseudorandom {@code long}, each conforming to the given origin |
|
779 * (inclusive) and bound (exclusive). |
|
780 * |
|
781 * <p>A pseudorandom {@code long} value is generated as if it's the result |
|
782 * of calling the following method with the origin and bound: |
|
783 * <pre> {@code |
|
784 * long nextLong(long origin, long bound) { |
|
785 * long r = nextLong(); |
|
786 * long n = bound - origin, m = n - 1; |
|
787 * if ((n & m) == 0L) // power of two |
|
788 * r = (r & m) + origin; |
|
789 * else if (n > 0L) { // reject over-represented candidates |
|
790 * for (long u = r >>> 1; // ensure nonnegative |
|
791 * u + m - (r = u % n) < 0L; // rejection check |
|
792 * u = nextLong() >>> 1) // retry |
|
793 * ; |
|
794 * r += origin; |
|
795 * } |
|
796 * else { // range not representable as long |
|
797 * while (r < origin || r >= bound) |
|
798 * r = nextLong(); |
|
799 * } |
|
800 * return r; |
|
801 * }}</pre> |
|
802 * |
|
803 * @param streamSize the number of values to generate |
|
804 * @param randomNumberOrigin the origin (inclusive) of each random value |
|
805 * @param randomNumberBound the bound (exclusive) of each random value |
|
806 * @return a stream of pseudorandom {@code long} values, |
|
807 * each with the given origin (inclusive) and bound (exclusive) |
|
808 * @throws IllegalArgumentException if {@code streamSize} is |
|
809 * less than zero, or {@code randomNumberOrigin} |
|
810 * is greater than or equal to {@code randomNumberBound} |
|
811 * @since 1.8 |
|
812 */ |
|
813 public LongStream longs(long streamSize, long randomNumberOrigin, |
|
814 long randomNumberBound) { |
|
815 if (streamSize < 0L) |
|
816 throw new IllegalArgumentException(BadSize); |
|
817 if (randomNumberOrigin >= randomNumberBound) |
|
818 throw new IllegalArgumentException(BadRange); |
|
819 return StreamSupport.longStream |
|
820 (new RandomLongsSpliterator |
|
821 (this, 0L, streamSize, randomNumberOrigin, randomNumberBound), |
|
822 false); |
|
823 } |
|
824 |
|
825 /** |
|
826 * Returns an effectively unlimited stream of pseudorandom {@code |
|
827 * long} values, each conforming to the given origin (inclusive) and bound |
|
828 * (exclusive). |
|
829 * |
|
830 * <p>A pseudorandom {@code long} value is generated as if it's the result |
|
831 * of calling the following method with the origin and bound: |
|
832 * <pre> {@code |
|
833 * long nextLong(long origin, long bound) { |
|
834 * long r = nextLong(); |
|
835 * long n = bound - origin, m = n - 1; |
|
836 * if ((n & m) == 0L) // power of two |
|
837 * r = (r & m) + origin; |
|
838 * else if (n > 0L) { // reject over-represented candidates |
|
839 * for (long u = r >>> 1; // ensure nonnegative |
|
840 * u + m - (r = u % n) < 0L; // rejection check |
|
841 * u = nextLong() >>> 1) // retry |
|
842 * ; |
|
843 * r += origin; |
|
844 * } |
|
845 * else { // range not representable as long |
|
846 * while (r < origin || r >= bound) |
|
847 * r = nextLong(); |
|
848 * } |
|
849 * return r; |
|
850 * }}</pre> |
|
851 * |
|
852 * @implNote This method is implemented to be equivalent to {@code |
|
853 * longs(Long.MAX_VALUE, randomNumberOrigin, randomNumberBound)}. |
|
854 * |
|
855 * @param randomNumberOrigin the origin (inclusive) of each random value |
|
856 * @param randomNumberBound the bound (exclusive) of each random value |
|
857 * @return a stream of pseudorandom {@code long} values, |
|
858 * each with the given origin (inclusive) and bound (exclusive) |
|
859 * @throws IllegalArgumentException if {@code randomNumberOrigin} |
|
860 * is greater than or equal to {@code randomNumberBound} |
|
861 * @since 1.8 |
|
862 */ |
|
863 public LongStream longs(long randomNumberOrigin, long randomNumberBound) { |
|
864 if (randomNumberOrigin >= randomNumberBound) |
|
865 throw new IllegalArgumentException(BadRange); |
|
866 return StreamSupport.longStream |
|
867 (new RandomLongsSpliterator |
|
868 (this, 0L, Long.MAX_VALUE, randomNumberOrigin, randomNumberBound), |
|
869 false); |
|
870 } |
|
871 |
|
872 /** |
|
873 * Returns a stream producing the given {@code streamSize} number of |
|
874 * pseudorandom {@code double} values, each between zero |
|
875 * (inclusive) and one (exclusive). |
|
876 * |
|
877 * <p>A pseudorandom {@code double} value is generated as if it's the result |
|
878 * of calling the method {@link #nextDouble()}. |
|
879 * |
|
880 * @param streamSize the number of values to generate |
|
881 * @return a stream of {@code double} values |
|
882 * @throws IllegalArgumentException if {@code streamSize} is |
|
883 * less than zero |
|
884 * @since 1.8 |
|
885 */ |
|
886 public DoubleStream doubles(long streamSize) { |
|
887 if (streamSize < 0L) |
|
888 throw new IllegalArgumentException(BadSize); |
|
889 return StreamSupport.doubleStream |
|
890 (new RandomDoublesSpliterator |
|
891 (this, 0L, streamSize, Double.MAX_VALUE, 0.0), |
|
892 false); |
|
893 } |
|
894 |
|
895 /** |
|
896 * Returns an effectively unlimited stream of pseudorandom {@code |
|
897 * double} values, each between zero (inclusive) and one |
|
898 * (exclusive). |
|
899 * |
|
900 * <p>A pseudorandom {@code double} value is generated as if it's the result |
|
901 * of calling the method {@link #nextDouble()}. |
|
902 * |
|
903 * @implNote This method is implemented to be equivalent to {@code |
|
904 * doubles(Long.MAX_VALUE)}. |
|
905 * |
|
906 * @return a stream of pseudorandom {@code double} values |
|
907 * @since 1.8 |
|
908 */ |
|
909 public DoubleStream doubles() { |
|
910 return StreamSupport.doubleStream |
|
911 (new RandomDoublesSpliterator |
|
912 (this, 0L, Long.MAX_VALUE, Double.MAX_VALUE, 0.0), |
|
913 false); |
|
914 } |
|
915 |
|
916 /** |
|
917 * Returns a stream producing the given {@code streamSize} number of |
|
918 * pseudorandom {@code double} values, each conforming to the given origin |
|
919 * (inclusive) and bound (exclusive). |
|
920 * |
|
921 * <p>A pseudorandom {@code double} value is generated as if it's the result |
|
922 * of calling the following method with the origin and bound: |
|
923 * <pre> {@code |
|
924 * double nextDouble(double origin, double bound) { |
|
925 * double r = nextDouble(); |
|
926 * r = r * (bound - origin) + origin; |
|
927 * if (r >= bound) // correct for rounding |
|
928 * r = Math.nextDown(bound); |
|
929 * return r; |
|
930 * }}</pre> |
|
931 * |
|
932 * @param streamSize the number of values to generate |
|
933 * @param randomNumberOrigin the origin (inclusive) of each random value |
|
934 * @param randomNumberBound the bound (exclusive) of each random value |
|
935 * @return a stream of pseudorandom {@code double} values, |
|
936 * each with the given origin (inclusive) and bound (exclusive) |
|
937 * @throws IllegalArgumentException if {@code streamSize} is |
|
938 * less than zero |
|
939 * @throws IllegalArgumentException if {@code randomNumberOrigin} |
|
940 * is greater than or equal to {@code randomNumberBound} |
|
941 * @since 1.8 |
|
942 */ |
|
943 public DoubleStream doubles(long streamSize, double randomNumberOrigin, |
|
944 double randomNumberBound) { |
|
945 if (streamSize < 0L) |
|
946 throw new IllegalArgumentException(BadSize); |
|
947 if (!(randomNumberOrigin < randomNumberBound)) |
|
948 throw new IllegalArgumentException(BadRange); |
|
949 return StreamSupport.doubleStream |
|
950 (new RandomDoublesSpliterator |
|
951 (this, 0L, streamSize, randomNumberOrigin, randomNumberBound), |
|
952 false); |
|
953 } |
|
954 |
|
955 /** |
|
956 * Returns an effectively unlimited stream of pseudorandom {@code |
|
957 * double} values, each conforming to the given origin (inclusive) and bound |
|
958 * (exclusive). |
|
959 * |
|
960 * <p>A pseudorandom {@code double} value is generated as if it's the result |
|
961 * of calling the following method with the origin and bound: |
|
962 * <pre> {@code |
|
963 * double nextDouble(double origin, double bound) { |
|
964 * double r = nextDouble(); |
|
965 * r = r * (bound - origin) + origin; |
|
966 * if (r >= bound) // correct for rounding |
|
967 * r = Math.nextDown(bound); |
|
968 * return r; |
|
969 * }}</pre> |
|
970 * |
|
971 * @implNote This method is implemented to be equivalent to {@code |
|
972 * doubles(Long.MAX_VALUE, randomNumberOrigin, randomNumberBound)}. |
|
973 * |
|
974 * @param randomNumberOrigin the origin (inclusive) of each random value |
|
975 * @param randomNumberBound the bound (exclusive) of each random value |
|
976 * @return a stream of pseudorandom {@code double} values, |
|
977 * each with the given origin (inclusive) and bound (exclusive) |
|
978 * @throws IllegalArgumentException if {@code randomNumberOrigin} |
|
979 * is greater than or equal to {@code randomNumberBound} |
|
980 * @since 1.8 |
|
981 */ |
|
982 public DoubleStream doubles(double randomNumberOrigin, double randomNumberBound) { |
|
983 if (!(randomNumberOrigin < randomNumberBound)) |
|
984 throw new IllegalArgumentException(BadRange); |
|
985 return StreamSupport.doubleStream |
|
986 (new RandomDoublesSpliterator |
|
987 (this, 0L, Long.MAX_VALUE, randomNumberOrigin, randomNumberBound), |
|
988 false); |
|
989 } |
|
990 |
|
991 /** |
|
992 * Spliterator for int streams. We multiplex the four int |
|
993 * versions into one class by treating a bound less than origin as |
|
994 * unbounded, and also by treating "infinite" as equivalent to |
|
995 * Long.MAX_VALUE. For splits, it uses the standard divide-by-two |
|
996 * approach. The long and double versions of this class are |
|
997 * identical except for types. |
|
998 */ |
|
999 static final class RandomIntsSpliterator implements Spliterator.OfInt { |
|
1000 final Random rng; |
|
1001 long index; |
|
1002 final long fence; |
|
1003 final int origin; |
|
1004 final int bound; |
|
1005 RandomIntsSpliterator(Random rng, long index, long fence, |
|
1006 int origin, int bound) { |
|
1007 this.rng = rng; this.index = index; this.fence = fence; |
|
1008 this.origin = origin; this.bound = bound; |
|
1009 } |
|
1010 |
|
1011 public RandomIntsSpliterator trySplit() { |
|
1012 long i = index, m = (i + fence) >>> 1; |
|
1013 return (m <= i) ? null : |
|
1014 new RandomIntsSpliterator(rng, i, index = m, origin, bound); |
|
1015 } |
|
1016 |
|
1017 public long estimateSize() { |
|
1018 return fence - index; |
|
1019 } |
|
1020 |
|
1021 public int characteristics() { |
|
1022 return (Spliterator.SIZED | Spliterator.SUBSIZED | |
|
1023 Spliterator.NONNULL | Spliterator.IMMUTABLE); |
|
1024 } |
|
1025 |
|
1026 public boolean tryAdvance(IntConsumer consumer) { |
|
1027 if (consumer == null) throw new NullPointerException(); |
|
1028 long i = index, f = fence; |
|
1029 if (i < f) { |
|
1030 consumer.accept(rng.internalNextInt(origin, bound)); |
|
1031 index = i + 1; |
|
1032 return true; |
|
1033 } |
|
1034 return false; |
|
1035 } |
|
1036 |
|
1037 public void forEachRemaining(IntConsumer consumer) { |
|
1038 if (consumer == null) throw new NullPointerException(); |
|
1039 long i = index, f = fence; |
|
1040 if (i < f) { |
|
1041 index = f; |
|
1042 Random r = rng; |
|
1043 int o = origin, b = bound; |
|
1044 do { |
|
1045 consumer.accept(r.internalNextInt(o, b)); |
|
1046 } while (++i < f); |
|
1047 } |
|
1048 } |
|
1049 } |
|
1050 |
|
1051 /** |
|
1052 * Spliterator for long streams. |
|
1053 */ |
|
1054 static final class RandomLongsSpliterator implements Spliterator.OfLong { |
|
1055 final Random rng; |
|
1056 long index; |
|
1057 final long fence; |
|
1058 final long origin; |
|
1059 final long bound; |
|
1060 RandomLongsSpliterator(Random rng, long index, long fence, |
|
1061 long origin, long bound) { |
|
1062 this.rng = rng; this.index = index; this.fence = fence; |
|
1063 this.origin = origin; this.bound = bound; |
|
1064 } |
|
1065 |
|
1066 public RandomLongsSpliterator trySplit() { |
|
1067 long i = index, m = (i + fence) >>> 1; |
|
1068 return (m <= i) ? null : |
|
1069 new RandomLongsSpliterator(rng, i, index = m, origin, bound); |
|
1070 } |
|
1071 |
|
1072 public long estimateSize() { |
|
1073 return fence - index; |
|
1074 } |
|
1075 |
|
1076 public int characteristics() { |
|
1077 return (Spliterator.SIZED | Spliterator.SUBSIZED | |
|
1078 Spliterator.NONNULL | Spliterator.IMMUTABLE); |
|
1079 } |
|
1080 |
|
1081 public boolean tryAdvance(LongConsumer consumer) { |
|
1082 if (consumer == null) throw new NullPointerException(); |
|
1083 long i = index, f = fence; |
|
1084 if (i < f) { |
|
1085 consumer.accept(rng.internalNextLong(origin, bound)); |
|
1086 index = i + 1; |
|
1087 return true; |
|
1088 } |
|
1089 return false; |
|
1090 } |
|
1091 |
|
1092 public void forEachRemaining(LongConsumer consumer) { |
|
1093 if (consumer == null) throw new NullPointerException(); |
|
1094 long i = index, f = fence; |
|
1095 if (i < f) { |
|
1096 index = f; |
|
1097 Random r = rng; |
|
1098 long o = origin, b = bound; |
|
1099 do { |
|
1100 consumer.accept(r.internalNextLong(o, b)); |
|
1101 } while (++i < f); |
|
1102 } |
|
1103 } |
|
1104 |
|
1105 } |
|
1106 |
|
1107 /** |
|
1108 * Spliterator for double streams. |
|
1109 */ |
|
1110 static final class RandomDoublesSpliterator implements Spliterator.OfDouble { |
|
1111 final Random rng; |
|
1112 long index; |
|
1113 final long fence; |
|
1114 final double origin; |
|
1115 final double bound; |
|
1116 RandomDoublesSpliterator(Random rng, long index, long fence, |
|
1117 double origin, double bound) { |
|
1118 this.rng = rng; this.index = index; this.fence = fence; |
|
1119 this.origin = origin; this.bound = bound; |
|
1120 } |
|
1121 |
|
1122 public RandomDoublesSpliterator trySplit() { |
|
1123 long i = index, m = (i + fence) >>> 1; |
|
1124 return (m <= i) ? null : |
|
1125 new RandomDoublesSpliterator(rng, i, index = m, origin, bound); |
|
1126 } |
|
1127 |
|
1128 public long estimateSize() { |
|
1129 return fence - index; |
|
1130 } |
|
1131 |
|
1132 public int characteristics() { |
|
1133 return (Spliterator.SIZED | Spliterator.SUBSIZED | |
|
1134 Spliterator.NONNULL | Spliterator.IMMUTABLE); |
|
1135 } |
|
1136 |
|
1137 public boolean tryAdvance(DoubleConsumer consumer) { |
|
1138 if (consumer == null) throw new NullPointerException(); |
|
1139 long i = index, f = fence; |
|
1140 if (i < f) { |
|
1141 consumer.accept(rng.internalNextDouble(origin, bound)); |
|
1142 index = i + 1; |
|
1143 return true; |
|
1144 } |
|
1145 return false; |
|
1146 } |
|
1147 |
|
1148 public void forEachRemaining(DoubleConsumer consumer) { |
|
1149 if (consumer == null) throw new NullPointerException(); |
|
1150 long i = index, f = fence; |
|
1151 if (i < f) { |
|
1152 index = f; |
|
1153 Random r = rng; |
|
1154 double o = origin, b = bound; |
|
1155 do { |
|
1156 consumer.accept(r.internalNextDouble(o, b)); |
|
1157 } while (++i < f); |
|
1158 } |
|
1159 } |
|
1160 } |
|
1161 |
|
1162 /** |
503 /** |
1163 * Serializable fields for Random. |
504 * Serializable fields for Random. |
1164 * |
505 * |
1165 * @serialField seed long |
506 * @serialField seed long |
1166 * seed for random computations |
507 * seed for random computations |
1226 } catch (Exception ex) { throw new Error(ex); } |
567 } catch (Exception ex) { throw new Error(ex); } |
1227 } |
568 } |
1228 private void resetSeed(long seedVal) { |
569 private void resetSeed(long seedVal) { |
1229 unsafe.putReferenceVolatile(this, seedOffset, new AtomicLong(seedVal)); |
570 unsafe.putReferenceVolatile(this, seedOffset, new AtomicLong(seedVal)); |
1230 } |
571 } |
|
572 |
|
573 // Methods required by class AbstractSpliteratorGenerator |
|
574 public Spliterator.OfInt makeIntsSpliterator(long index, long fence, int origin, int bound) { |
|
575 return new RandomIntsSpliterator(this, index, fence, origin, bound); |
|
576 } |
|
577 public Spliterator.OfLong makeLongsSpliterator(long index, long fence, long origin, long bound) { |
|
578 return new RandomLongsSpliterator(this, index, fence, origin, bound); |
|
579 } |
|
580 public Spliterator.OfDouble makeDoublesSpliterator(long index, long fence, double origin, double bound) { |
|
581 return new RandomDoublesSpliterator(this, index, fence, origin, bound); |
|
582 } |
|
583 |
|
584 /** |
|
585 * Spliterators for producing streams. These are based on abstract spliterator classes provided |
|
586 * by class AbstractSpliteratorGenerator. Each one needs to define only a constructor and two |
|
587 * methods. |
|
588 */ |
|
589 static class RandomIntsSpliterator extends RandomSupport.RandomSpliterator |
|
590 implements Spliterator.OfInt { |
|
591 final AbstractSpliteratorGenerator generatingGenerator; |
|
592 final int origin; |
|
593 final int bound; |
|
594 |
|
595 RandomIntsSpliterator(AbstractSpliteratorGenerator generatingGenerator, |
|
596 long index, long fence, int origin, int bound) { |
|
597 super(index, fence); |
|
598 this.generatingGenerator = generatingGenerator; |
|
599 this.origin = origin; this.bound = bound; |
|
600 } |
|
601 |
|
602 public Spliterator.OfInt trySplit() { |
|
603 long i = index, m = (i + fence) >>> 1; |
|
604 if (m <= i) return null; |
|
605 index = m; |
|
606 // The same generatingGenerator is used, with no splitting or copying. |
|
607 return new RandomIntsSpliterator(generatingGenerator, i, m, origin, bound); |
|
608 } |
|
609 |
|
610 public boolean tryAdvance(IntConsumer consumer) { |
|
611 if (consumer == null) throw new NullPointerException(); |
|
612 long i = index, f = fence; |
|
613 if (i < f) { |
|
614 consumer.accept(RandomSupport.boundedNextInt(generatingGenerator, origin, bound)); |
|
615 index = i + 1; |
|
616 return true; |
|
617 } |
|
618 else return false; |
|
619 } |
|
620 |
|
621 public void forEachRemaining(IntConsumer consumer) { |
|
622 if (consumer == null) throw new NullPointerException(); |
|
623 long i = index, f = fence; |
|
624 if (i < f) { |
|
625 index = f; |
|
626 RandomGenerator r = generatingGenerator; |
|
627 int o = origin, b = bound; |
|
628 do { |
|
629 consumer.accept(RandomSupport.boundedNextInt(r, o, b)); |
|
630 } while (++i < f); |
|
631 } |
|
632 } |
|
633 } |
|
634 |
|
635 /** |
|
636 * Spliterator for long streams. |
|
637 */ |
|
638 static class RandomLongsSpliterator extends RandomSupport.RandomSpliterator |
|
639 implements Spliterator.OfLong { |
|
640 final AbstractSpliteratorGenerator generatingGenerator; |
|
641 final long origin; |
|
642 final long bound; |
|
643 |
|
644 RandomLongsSpliterator(AbstractSpliteratorGenerator generatingGenerator, |
|
645 long index, long fence, long origin, long bound) { |
|
646 super(index, fence); |
|
647 this.generatingGenerator = generatingGenerator; |
|
648 this.origin = origin; this.bound = bound; |
|
649 } |
|
650 |
|
651 public Spliterator.OfLong trySplit() { |
|
652 long i = index, m = (i + fence) >>> 1; |
|
653 if (m <= i) return null; |
|
654 index = m; |
|
655 // The same generatingGenerator is used, with no splitting or copying. |
|
656 return new RandomLongsSpliterator(generatingGenerator, i, m, origin, bound); |
|
657 } |
|
658 |
|
659 public boolean tryAdvance(LongConsumer consumer) { |
|
660 if (consumer == null) throw new NullPointerException(); |
|
661 long i = index, f = fence; |
|
662 if (i < f) { |
|
663 consumer.accept(RandomSupport.boundedNextLong(generatingGenerator, origin, bound)); |
|
664 index = i + 1; |
|
665 return true; |
|
666 } |
|
667 else return false; |
|
668 } |
|
669 |
|
670 public void forEachRemaining(LongConsumer consumer) { |
|
671 if (consumer == null) throw new NullPointerException(); |
|
672 long i = index, f = fence; |
|
673 if (i < f) { |
|
674 index = f; |
|
675 RandomGenerator r = generatingGenerator; |
|
676 long o = origin, b = bound; |
|
677 do { |
|
678 consumer.accept(RandomSupport.boundedNextLong(r, o, b)); |
|
679 } while (++i < f); |
|
680 } |
|
681 } |
|
682 } |
|
683 |
|
684 /** |
|
685 * Spliterator for double streams. |
|
686 */ |
|
687 static class RandomDoublesSpliterator extends RandomSupport.RandomSpliterator |
|
688 implements Spliterator.OfDouble { |
|
689 final AbstractSpliteratorGenerator generatingGenerator; |
|
690 final double origin; |
|
691 final double bound; |
|
692 |
|
693 RandomDoublesSpliterator(AbstractSpliteratorGenerator generatingGenerator, |
|
694 long index, long fence, double origin, double bound) { |
|
695 super(index, fence); |
|
696 this.generatingGenerator = generatingGenerator; |
|
697 this.origin = origin; this.bound = bound; |
|
698 } |
|
699 |
|
700 public Spliterator.OfDouble trySplit() { |
|
701 long i = index, m = (i + fence) >>> 1; |
|
702 if (m <= i) return null; |
|
703 index = m; |
|
704 // The same generatingGenerator is used, with no splitting or copying. |
|
705 return new RandomDoublesSpliterator(generatingGenerator, i, m, origin, bound); |
|
706 } |
|
707 |
|
708 public boolean tryAdvance(DoubleConsumer consumer) { |
|
709 if (consumer == null) throw new NullPointerException(); |
|
710 long i = index, f = fence; |
|
711 if (i < f) { |
|
712 consumer.accept(RandomSupport.boundedNextDouble(generatingGenerator, origin, bound)); |
|
713 index = i + 1; |
|
714 return true; |
|
715 } |
|
716 else return false; |
|
717 } |
|
718 |
|
719 public void forEachRemaining(DoubleConsumer consumer) { |
|
720 if (consumer == null) throw new NullPointerException(); |
|
721 long i = index, f = fence; |
|
722 if (i < f) { |
|
723 index = f; |
|
724 RandomGenerator r = generatingGenerator; |
|
725 double o = origin, b = bound; |
|
726 do { |
|
727 consumer.accept(RandomSupport.boundedNextDouble(r, o, b)); |
|
728 } while (++i < f); |
|
729 } |
|
730 } |
|
731 } |
1231 } |
732 } |