sequence.hpp Source File

sequence.hpp Source File#

Composable Kernel: sequence.hpp Source File
tile/core/container/sequence.hpp
Go to the documentation of this file.
1// SPDX-License-Identifier: MIT
2// Copyright (c) 2018-2024, Advanced Micro Devices, Inc. All rights reserved.
3
4#pragma once
5
13
14namespace ck_tile {
15
16template <index_t...>
17struct sequence;
18
19template <typename Seq, index_t I>
20struct sequence_split;
21
22template <typename>
24
25template <typename>
27
28template <typename>
30
31template <index_t I, index_t... Is>
33
34template <typename Seq>
35CK_TILE_HOST_DEVICE constexpr auto sequence_pop_back(Seq);
36
37namespace impl {
38// static_assert(__has_builtin(__type_pack_element), "can't find __type_pack_element");
39template <index_t I, typename... Ts>
40using at_index_t = __type_pack_element<I, Ts...>;
41} // namespace impl
42
43// we could implement as below, similiar to std. But let's reduce the symbol name...
44// template< class T, T... Ints >
45// class integer_sequence;
46
47template <index_t... Is>
49{
50 using type = sequence;
52
53 CK_TILE_HOST_DEVICE static constexpr index_t size() { return sizeof...(Is); }
54 CK_TILE_HOST_DEVICE static constexpr bool is_static() { return true; };
55
56 template <index_t I>
57 CK_TILE_HOST_DEVICE static constexpr auto get()
58 {
59 static_assert(I < size(), "wrong! I too large");
61 }
62
63 template <index_t I>
64 CK_TILE_HOST_DEVICE static constexpr auto get(number<I>)
65 {
66 static_assert(I < size(), "wrong! I too large");
67 return number<get<I>()>{};
68 }
69
71 {
72 // the last dummy element is to prevent compiler complain about empty array, when mSize = 0
73 const index_t mData[size() + 1] = {Is..., 0};
74 return mData[I];
75 }
76
77 template <index_t I>
78 CK_TILE_HOST_DEVICE static constexpr auto at()
79 {
80 static_assert(I < size(), "wrong! I too large");
82 }
83
84 template <index_t I>
85 CK_TILE_HOST_DEVICE static constexpr auto at(number<I>)
86 {
87 static_assert(I < size(), "wrong! I too large");
88 return number<get<I>()>{};
89 }
90
91 template <typename I>
92 CK_TILE_HOST_DEVICE constexpr auto operator[](I i) const
93 {
94 return at(i);
95 }
96
97 template <index_t... IRs>
98 CK_TILE_HOST_DEVICE static constexpr auto reorder_new_to_old(sequence<IRs...> /*new2old*/)
99 {
100 static_assert(sizeof...(Is) == sizeof...(IRs),
101 "wrong! reorder map should have the same size as sequence to be rerodered");
102
103 static_assert(is_valid_sequence_map<sequence<IRs...>>::value, "wrong! invalid reorder map");
104
105 return sequence<type::get(number<IRs>{})...>{};
106 }
107
108 // MapOld2New is sequence<...>
109 template <typename MapOld2New>
110 CK_TILE_HOST_DEVICE static constexpr auto reorder_old_to_new(MapOld2New)
111 {
112 static_assert(MapOld2New::size() == size(),
113 "wrong! reorder map should have the same size as sequence to be rerodered");
114
115 static_assert(is_valid_sequence_map<MapOld2New>::value, "wrong! invalid reorder map");
116
118 }
119
120 CK_TILE_HOST_DEVICE static constexpr auto reverse()
121 {
122 return typename sequence_reverse<type>::type{};
123 }
124
125 CK_TILE_HOST_DEVICE static constexpr auto front()
126 {
127 static_assert(size() > 0, "wrong!");
128 return get(number<0>{});
129 }
130
131 CK_TILE_HOST_DEVICE static constexpr auto back()
132 {
133 static_assert(size() > 0, "wrong!");
134 return get(number<size() - 1>{});
135 }
136
137 CK_TILE_HOST_DEVICE static constexpr auto pop_front() { return sequence_pop_front(type{}); }
138
139 CK_TILE_HOST_DEVICE static constexpr auto pop_back() { return sequence_pop_back(type{}); }
140
141 template <index_t... Xs>
143 {
144 return sequence<Xs..., Is...>{};
145 }
146
147 template <index_t... Xs>
148 CK_TILE_HOST_DEVICE static constexpr auto push_front(number<Xs>...)
149 {
150 return sequence<Xs..., Is...>{};
151 }
152
153 template <index_t... Xs>
155 {
156 return sequence<Is..., Xs...>{};
157 }
158
159 template <index_t... Xs>
160 CK_TILE_HOST_DEVICE static constexpr auto push_back(number<Xs>...)
161 {
162 return sequence<Is..., Xs...>{};
163 }
164
165 // pickup element at index <Ids...>
166 template <index_t... Ids>
167 CK_TILE_HOST_DEVICE static constexpr auto extract(number<Ids>...)
168 {
169 return sequence<type::get(number<Ids>{})...>{};
170 }
171
172 template <index_t... Ids>
174 {
175 return sequence<type::get(number<Ids>{})...>{};
176 }
177
178 CK_TILE_HOST_DEVICE static constexpr auto sum() { return (Is + ... + 0); }
179 CK_TILE_HOST_DEVICE static constexpr auto product() { return (Is * ... * 1); }
180
181 // modify element at index "I" with value "X"
182 template <index_t I, index_t X>
184 {
185 static_assert(I < size(), "wrong!");
186
187 using seq_split = sequence_split<type, I>;
188 constexpr auto seq_left = typename seq_split::left_type{};
189 constexpr auto seq_right = typename seq_split::right_type{}.pop_front();
190
191 return seq_left.push_back(number<X>{}).push_back(seq_right);
192 }
193
194 template <typename F>
195 CK_TILE_HOST_DEVICE static constexpr auto transform(F f)
196 {
197 return sequence<f(Is)...>{};
198 }
199};
200
201template <index_t... Is>
202CK_TILE_HOST_DEVICE static void print(const sequence<Is...>&)
203{
204 printf("sequence<");
205 if constexpr(sizeof...(Is) > 0)
206 {
207 bool first = true;
208 (([&first](index_t value) {
209 printf("%s%d", first ? "" : ", ", value);
210 first = false;
211 }(Is)),
212 ...);
213 }
214 printf(">");
215}
216
217namespace impl {
218template <typename T, T... Ints>
220
221template <index_t... Ints>
223{
224 using seq_type = sequence<Ints...>;
225};
226} // namespace impl
227
228// similiar
229template <index_t N>
231 typename __make_integer_seq<impl::__integer_sequence, index_t, N>::seq_type;
232
233// merge sequence
234template <typename Seq, typename... Seqs>
236{
237 using type = typename sequence_merge<Seq, typename sequence_merge<Seqs...>::type>::type;
238};
239
240template <index_t... Xs, index_t... Ys>
241struct sequence_merge<sequence<Xs...>, sequence<Ys...>>
242{
243 using type = sequence<Xs..., Ys...>;
244};
245
246template <typename Seq>
247struct sequence_merge<Seq>
248{
249 using type = Seq;
250};
251
252// generate sequence
253template <index_t NSize, typename F>
255{
256 template <index_t IBegin, index_t NRemain, typename G>
258 {
259 static constexpr index_t NRemainLeft = NRemain / 2;
260 static constexpr index_t NRemainRight = NRemain - NRemainLeft;
261 static constexpr index_t IMiddle = IBegin + NRemainLeft;
262
263 using type = typename sequence_merge<
266 };
267
268 template <index_t I, typename G>
269 struct sequence_gen_impl<I, 1, G>
270 {
271 static constexpr index_t Is = G{}(number<I>{});
273 };
274
275 template <index_t I, typename G>
276 struct sequence_gen_impl<I, 0, G>
277 {
279 };
280
282};
283
284// arithmetic sequence
285template <index_t IBegin, index_t IEnd, index_t Increment>
287{
288 struct F
289 {
291 {
292 return i * Increment + IBegin;
293 }
294 };
295
296 using type0 = typename sequence_gen<(IEnd - IBegin) / Increment, F>::type;
298
299 static constexpr bool kHasContent =
300 (Increment > 0 && IBegin < IEnd) || (Increment < 0 && IBegin > IEnd);
301
302 using type = typename std::conditional<kHasContent, type0, type1>::type;
303};
304
305template <index_t IEnd>
306struct arithmetic_sequence_gen<0, IEnd, 1>
307{
309};
310
311// uniform sequence
312template <index_t NSize, index_t I>
314{
315 struct F
316 {
317 CK_TILE_HOST_DEVICE constexpr index_t operator()(index_t) const { return I; }
318 };
319
321};
322
323// reverse inclusive scan (with init) sequence
324template <typename, typename, index_t>
326
327template <index_t I, index_t... Is, typename Reduce, index_t Init>
329{
331
332 static constexpr index_t new_reduce = Reduce{}(I, old_scan{}.front());
333
335};
336
337template <index_t I, typename Reduce, index_t Init>
339{
340 using type = sequence<Reduce{}(I, Init)>;
341};
342
343template <typename Reduce, index_t Init>
348
349// split sequence
350template <typename Seq, index_t I>
352{
353 static constexpr index_t NSize = Seq{}.size();
354
357
358 using left_type = decltype(Seq::extract(range0{}));
359 using right_type = decltype(Seq::extract(range1{}));
360};
361
362#if 0
363// reverse sequence
364template <typename Seq>
365struct sequence_reverse
366{
367 static constexpr index_t NSize = Seq{}.size();
368
369 using seq_split = sequence_split<Seq, NSize / 2>;
370 using type = typename sequence_merge<
371 typename sequence_reverse<typename seq_split::right_type>::type,
372 typename sequence_reverse<typename seq_split::left_type>::type>::type;
373};
374
375template <index_t I>
376struct sequence_reverse<sequence<I>>
377{
378 using type = sequence<I>;
379};
380
381template <index_t I0, index_t I1>
382struct sequence_reverse<sequence<I0, I1>>
383{
384 using type = sequence<I1, I0>;
385};
386#endif
387
388namespace impl {
389template <typename Id, index_t... Ns>
391
392template <index_t... Ids, index_t... Ns>
393struct seq_reverse<sequence<Ids...>, Ns...>
394{
395 template <index_t I>
397 using type = sequence<element<(sizeof...(Ns) - 1 - Ids)>::value...>;
398};
399} // namespace impl
400
401template <index_t... Ns>
403 : impl::seq_reverse<make_index_sequence<sizeof...(Ns)>, Ns...>
404{
405};
406
407// template <index_t... Ns>
408// using sequence_reverse_t = typename sequence_reverse<Ns...>::type;
409
410#if 1
411template <typename Reduce, typename Seq, typename... Seqs>
413{
414 using type = typename sequence_reduce<Reduce,
415 Seq,
416 typename sequence_reduce<Reduce, Seqs...>::type>::type;
417};
418
419template <typename Reduce, index_t... Xs, index_t... Ys>
421{
422 using type = sequence<Reduce{}(Xs, Ys)...>;
423};
424
425template <typename Reduce, typename Seq>
427{
428 using type = Seq;
429};
430#endif
431
432template <typename Values, typename Ids, typename Compare>
434{
435 template <typename LeftValues,
436 typename LeftIds,
437 typename RightValues,
438 typename RightIds,
439 typename MergedValues,
440 typename MergedIds,
441 typename Comp>
443 {
444 static constexpr bool choose_left = LeftValues::front() < RightValues::front();
445
446 static constexpr index_t chosen_value =
447 choose_left ? LeftValues::front() : RightValues::front();
448 static constexpr index_t chosen_id = choose_left ? LeftIds::front() : RightIds::front();
449
450 using new_merged_values = decltype(MergedValues::push_back(number<chosen_value>{}));
451 using new_merged_ids = decltype(MergedIds::push_back(number<chosen_id>{}));
452
453 using new_left_values = typename std::
454 conditional<choose_left, decltype(LeftValues::pop_front()), LeftValues>::type;
456 typename std::conditional<choose_left, decltype(LeftIds::pop_front()), LeftIds>::type;
457
458 using new_right_values = typename std::
459 conditional<choose_left, RightValues, decltype(RightValues::pop_front())>::type;
461 typename std::conditional<choose_left, RightIds, decltype(RightIds::pop_front())>::type;
462
469 Comp>;
470 // this is output
473 };
474
475 template <typename LeftValues,
476 typename LeftIds,
477 typename MergedValues,
478 typename MergedIds,
479 typename Comp>
480 struct sorted_sequence_merge_impl<LeftValues,
481 LeftIds,
482 sequence<>,
483 sequence<>,
484 MergedValues,
485 MergedIds,
486 Comp>
487 {
490 };
491
492 template <typename RightValues,
493 typename RightIds,
494 typename MergedValues,
495 typename MergedIds,
496 typename Comp>
498 sequence<>,
499 RightValues,
500 RightIds,
501 MergedValues,
502 MergedIds,
503 Comp>
504 {
507 };
508
509 template <typename LeftValues,
510 typename LeftIds,
511 typename RightValues,
512 typename RightIds,
513 typename Comp>
515 {
517 LeftIds,
518 RightValues,
519 RightIds,
522 Comp>;
523
526 };
527
528 static constexpr index_t nsize = Values::size();
529
532
538
544
545 using merged_sorted = sorted_sequence_merge<left_sorted_values,
549 Compare>;
550
553};
554
555template <index_t ValueX, index_t ValueY, index_t IdX, index_t IdY, typename Compare>
556struct sequence_sort_impl<sequence<ValueX, ValueY>, sequence<IdX, IdY>, Compare>
557{
558 static constexpr bool choose_x = Compare{}(ValueX, ValueY);
559
560 using sorted_values = typename std::
561 conditional<choose_x, sequence<ValueX, ValueY>, sequence<ValueY, ValueX>>::type;
563 typename std::conditional<choose_x, sequence<IdX, IdY>, sequence<IdY, IdX>>::type;
564};
565
566template <index_t Value, index_t Id, typename Compare>
572
573template <typename Compare>
579
580template <typename Values, typename Compare>
582{
583 using unsorted_ids = typename arithmetic_sequence_gen<0, Values::size(), 1>::type;
585
586 // this is output
587 using type = typename sort::sorted_values;
589};
590
591template <typename Values, typename Less, typename Equal>
593{
594 template <typename RemainValues,
595 typename RemainIds,
596 typename UniquifiedValues,
597 typename UniquifiedIds,
598 typename Eq>
600 {
601 static constexpr index_t current_value = RemainValues::front();
602 static constexpr index_t current_id = RemainIds::front();
603
604 static constexpr bool is_unique_value = (current_value != UniquifiedValues::back());
605
606 using new_remain_values = decltype(RemainValues::pop_front());
607 using new_remain_ids = decltype(RemainIds::pop_front());
608
610 typename std::conditional<is_unique_value,
611 decltype(UniquifiedValues::push_back(
613 UniquifiedValues>::type;
614
616 typename std::conditional<is_unique_value,
617 decltype(UniquifiedIds::push_back(number<current_id>{})),
618 UniquifiedIds>::type;
619
624 Eq>;
625
626 // this is output
629 };
630
631 template <typename UniquifiedValues, typename UniquifiedIds, typename Eq>
633 sequence<>,
634 UniquifiedValues,
635 UniquifiedIds,
636 Eq>
637 {
638 using uniquified_values = UniquifiedValues;
639 using uniquified_ids = UniquifiedIds;
640 };
641
642 template <typename SortedValues, typename SortedIds, typename Eq>
644 {
645 using uniquify = sorted_sequence_uniquify_impl<decltype(SortedValues::pop_front()),
646 decltype(SortedIds::pop_front()),
647 sequence<SortedValues::front()>,
648 sequence<SortedIds::front()>,
649 Eq>;
650
653 };
654
656 using sorted_values = typename sort::type;
658
660
661 // this is output
664};
665
666template <typename SeqMap>
668 : std::is_same<typename arithmetic_sequence_gen<0, SeqMap::size(), 1>::type,
669 typename sequence_sort<SeqMap, less<index_t>>::type>
670{
671};
672
673template <typename SeqMap>
675{
676 template <typename X2Y, typename WorkingY2X, index_t XBegin, index_t XRemain>
678 {
679 static constexpr auto new_y2x =
680 WorkingY2X::modify(X2Y::get(number<XBegin>{}), number<XBegin>{});
681
682 using type =
683 typename sequence_map_inverse_impl<X2Y, decltype(new_y2x), XBegin + 1, XRemain - 1>::
684 type;
685 };
686
687 template <typename X2Y, typename WorkingY2X, index_t XBegin>
688 struct sequence_map_inverse_impl<X2Y, WorkingY2X, XBegin, 0>
689 {
690 using type = WorkingY2X;
691 };
692
693 using type =
694 typename sequence_map_inverse_impl<SeqMap,
695 typename uniform_sequence_gen<SeqMap::size(), 0>::type,
696 0,
697 SeqMap::size()>::type;
698};
699
700template <index_t... Xs, index_t... Ys>
702{
703 return ((Xs == Ys) && ...);
704}
705
706template <index_t... Xs, index_t... Ys>
708{
709 return !(x == y);
710}
711
712template <index_t... Xs, index_t... Ys>
714{
715 static_assert(sizeof...(Xs) == sizeof...(Ys), "wrong! inconsistent size");
716
717 return sequence<(Xs + Ys)...>{};
718}
719
720template <index_t... Xs, index_t... Ys>
722{
723 static_assert(sizeof...(Xs) == sizeof...(Ys), "wrong! inconsistent size");
724
725 return sequence<(Xs - Ys)...>{};
726}
727
728template <index_t... Xs, index_t... Ys>
730{
731 static_assert(sizeof...(Xs) == sizeof...(Ys), "wrong! inconsistent size");
732
733 return sequence<(Xs * Ys)...>{};
734}
735
736template <index_t... Xs, index_t... Ys>
738{
739 static_assert(sizeof...(Xs) == sizeof...(Ys), "wrong! inconsistent size");
740
741 return sequence<(Xs / Ys)...>{};
742}
743
744template <index_t... Xs, index_t... Ys>
746{
747 static_assert(sizeof...(Xs) == sizeof...(Ys), "wrong! inconsistent size");
748
749 return sequence<(Xs % Ys)...>{};
750}
751
752template <index_t... Xs, index_t Y>
754{
755 return sequence<(Xs + Y)...>{};
756}
757
758template <index_t... Xs, index_t Y>
760{
761 return sequence<(Xs - Y)...>{};
762}
763
764template <index_t... Xs, index_t Y>
766{
767 return sequence<(Xs * Y)...>{};
768}
769
770template <index_t... Xs, index_t Y>
772{
773 return sequence<(Xs / Y)...>{};
774}
775
776template <index_t... Xs, index_t Y>
778{
779 return sequence<(Xs % Y)...>{};
780}
781
782template <index_t Y, index_t... Xs>
784{
785 return sequence<(Y + Xs)...>{};
786}
787
788template <index_t Y, index_t... Xs>
790{
791 return sequence<(Y - Xs)...>{};
792}
793
794template <index_t Y, index_t... Xs>
796{
797 return sequence<(Y * Xs)...>{};
798}
799
800template <index_t Y, index_t... Xs>
802{
803 return sequence<(Y / Xs)...>{};
804}
805
806template <index_t Y, index_t... Xs>
808{
809 return sequence<(Y % Xs)...>{};
810}
811
812template <index_t I, index_t... Is>
814{
815 return sequence<Is...>{};
816}
817
818template <typename Seq>
820{
821 static_assert(Seq::size() > 0, "wrong! cannot pop an empty sequence!");
822 return sequence_pop_front(Seq::reverse()).reverse();
823}
824
825template <typename... Seqs>
827{
828 return typename sequence_merge<Seqs...>::type{};
829}
830
831template <typename F, index_t... Xs>
833{
834 return sequence<f(Xs)...>{};
835}
836
837template <typename F, index_t... Xs, index_t... Ys>
839{
840 static_assert(sequence<Xs...>::size() == sequence<Ys...>::size(), "Dim not the same");
841
842 return sequence<f(Xs, Ys)...>{};
843}
844
845template <typename F, index_t... Xs, index_t... Ys, index_t... Zs>
846CK_TILE_HOST_DEVICE constexpr auto
848{
849 static_assert(sequence<Xs...>::size() == sequence<Ys...>::size() &&
851 "Dim not the same");
852
853 return sequence<f(Xs, Ys, Zs)...>{};
854}
855
856template <typename Seq, typename Reduce, index_t Init>
861
862template <typename Seq, typename Reduce, index_t Init>
864{
865 return reverse_inclusive_scan_sequence(Seq::pop_front(), Reduce{}, number<Init>{})
866 .push_back(number<Init>{});
867}
868
869template <typename Seq, typename Reduce, index_t Init>
871{
872 return reverse_inclusive_scan_sequence(Seq{}.reverse(), Reduce{}, number<Init>{}).reverse();
873}
874
875// e.g. Seq<2, 3, 4> --> Seq<0, 2, 5>, Init=0, Reduce=Add
876// ResultSeq TargetSeq Reduce
877template <typename, typename, typename>
879
880template <index_t... Xs, index_t Y, index_t... Ys, typename Reduce>
882{
883 using old_scan = typename sequence_merge<sequence<Xs...>,
884 sequence<Reduce{}(Y, sequence<Xs...>{}.back())>>::type;
886};
887
888template <index_t... Xs, index_t Y, typename Reduce>
890{
891 using type = sequence<Xs...>;
892};
893
894template <index_t... Xs, typename Reduce>
896{
897 using type = sequence<Xs...>;
898};
899
900template <typename Seq, typename Reduce, index_t Init>
902{
903 // TODO: c++20 and later can pass in Reduce with a lambda expression
904 return typename sequence_exclusive_scan<sequence<Init>, Seq, Reduce>::type{};
905}
906
907template <typename Seq>
908constexpr auto prefix_sum_sequence(Seq)
909{
911 typename sequence_merge<Seq, sequence<0>>::type,
912 plus<index_t>>::type{};
913}
914
915template <typename Seq, index_t... Is>
917{
918 return sequence<Seq::get(number<Is>{})...>{};
919}
920
921#if 1
922namespace detail {
923template <typename WorkSeq, typename RemainSeq, typename RemainMask>
925{
926 using new_work_seq = typename std::conditional<RemainMask::front(),
927 decltype(WorkSeq::push_back(RemainSeq::front())),
928 WorkSeq>::type;
929
930 using type =
932 decltype(RemainSeq::pop_front()),
933 decltype(RemainMask::pop_front())>::type;
934};
935
936template <typename WorkSeq>
938{
939 using type = WorkSeq;
940};
941
942} // namespace detail
943
944template <typename Seq, typename Mask>
946{
947 static_assert(Seq::size() == Mask::size(), "wrong!");
948
949 return typename detail::pick_sequence_elements_by_mask_impl<sequence<>, Seq, Mask>::type{};
950}
951
952namespace detail {
953template <typename WorkSeq, typename RemainValues, typename RemainIds>
955{
956 using new_work_seq = decltype(WorkSeq::modify(RemainIds::front(), RemainValues::front()));
957
958 using type =
960 decltype(RemainValues::pop_front()),
961 decltype(RemainIds::pop_front())>::type;
962};
963
964template <typename WorkSeq>
966{
967 using type = WorkSeq;
968};
969} // namespace detail
970
971template <typename Seq, typename Values, typename Ids>
973{
974 static_assert(Values::size() == Ids::size() && Seq::size() >= Values::size(), "wrong!");
975
977}
978#endif
979
980template <typename Seq, typename Reduce, index_t Init>
982reduce_on_sequence(Seq, Reduce f, number<Init> /*initial_value*/)
983{
984 index_t result = Init;
985
986 for(index_t i = 0; i < Seq::size(); ++i)
987 {
988 result = f(result, Seq::at(i));
989 }
990
991 return result;
992}
993
994// TODO: a generic any_of for any container
995template <typename Seq, typename F>
996CK_TILE_HOST_DEVICE constexpr bool sequence_any_of(Seq, F f)
997{
998 bool flag = false;
999
1000 for(index_t i = 0; i < Seq::size(); ++i)
1001 {
1002 flag = flag || f(Seq::at(i));
1003 }
1004
1005 return flag;
1006}
1007
1008// TODO: a generic all_of for any container
1009template <typename Seq, typename F>
1010CK_TILE_HOST_DEVICE constexpr bool sequence_all_of(Seq, F f)
1011{
1012 bool flag = true;
1013
1014 for(index_t i = 0; i < Seq::size(); ++i)
1015 {
1016 flag = flag && f(Seq::at(i));
1017 }
1018
1019 return flag;
1020}
1021
1022template <typename... Seqs>
1023using sequence_merge_t = typename sequence_merge<Seqs...>::type;
1024
1025template <index_t NSize, index_t I>
1027
1028template <index_t... Is>
1030{
1031 return sequence<Is...>{};
1032}
1033
1034// F() returns index_t
1035// F use default constructor, so F cannot be lambda function
1036template <typename F, index_t N>
1038{
1039 return typename sequence_gen<N, F>::type{};
1040}
1041
1042// F() returns number<>
1043// F could be lambda function
1044template <typename F, index_t N>
1046{
1047 return unpack([&f](auto&&... xs) { return make_sequence(f(xs)...); },
1049}
1050
1051template <class... T>
1052struct tuple;
1053
1054template <index_t... Is>
1056{
1057 return sequence<Is...>{};
1058}
1059
1060namespace detail {
1061template <index_t h_idx, typename SeqSortedSamples, typename SeqRange>
1063
1064template <index_t h_idx, index_t x, index_t... xs, index_t r, index_t... rs>
1065struct sorted_sequence_histogram<h_idx, sequence<x, xs...>, sequence<r, rs...>>
1066{
1067 template <typename Histogram>
1068 constexpr auto operator()(Histogram& h)
1069 {
1070 if constexpr(x < r)
1071 {
1072 h.template at<h_idx>() += 1;
1073 sorted_sequence_histogram<h_idx, sequence<xs...>, sequence<r, rs...>>{}(h);
1074 }
1075 else
1076 {
1077 h.template at<h_idx + 1>() = 1;
1078 sorted_sequence_histogram<h_idx + 1, sequence<xs...>, sequence<rs...>>{}(h);
1079 }
1080 }
1081};
1082
1083template <index_t h_idx, index_t x, index_t r, index_t... rs>
1084struct sorted_sequence_histogram<h_idx, sequence<x>, sequence<r, rs...>>
1085{
1086 template <typename Histogram>
1087 constexpr auto operator()(Histogram& h)
1088 {
1089 if constexpr(x < r)
1090 {
1091 h.template at<h_idx>() += 1;
1092 }
1093 }
1094};
1095} // namespace detail
1096
1097template <typename, index_t>
1098struct array; // declare for later use (array->seq utility)
1099
1100// SeqSortedSamples: <0, 2, 3, 5, 7>, SeqRange: <0, 3, 6, 9> -> SeqHistogram : <2, 2, 1>
1101template <typename SeqSortedSamples, index_t r, index_t... rs>
1103{
1104 constexpr auto bins = sizeof...(rs); // or categories
1105 constexpr auto histogram = [&]() {
1106 array<index_t, bins> h{0}; // make sure this can clear all element to zero
1107 detail::sorted_sequence_histogram<0, SeqSortedSamples, sequence<rs...>>{}(h);
1108 return h;
1109 }();
1110
1111 return TO_SEQUENCE(histogram, bins);
1112}
1113
1114template <typename F, index_t N>
1116{
1117 using T = remove_cvref_t<decltype(f(number<0>{}))>;
1118
1119 return unpack([&f](auto&&... is) { return array<T, N>{f(is)...}; },
1121}
1122
1123namespace impl {
1124template <typename, typename, typename, index_t>
1126
1127template <index_t x,
1128 index_t... xs,
1129 index_t m,
1130 index_t... ms,
1131 index_t id,
1132 index_t... ids,
1133 index_t SliceSize>
1135 sequence<m, ms...>,
1136 sequence<id, ids...>,
1137 SliceSize>
1138{
1139 using old_scan =
1140 reverse_slice_sequence_impl<sequence<xs...>, sequence<ms...>, sequence<ids...>, SliceSize>;
1141
1142 static constexpr auto slice_size = old_scan::remaining_slice_sizes::front().value;
1143 static constexpr auto slice_length =
1144 std::conditional_t<m, number<gcd(x, slice_size)>, number<x>>::value;
1145
1147 typename sequence_merge<sequence<slice_length>, typename old_scan::dim_lengths>::type;
1149 typename sequence_merge<sequence<x / slice_length>, typename old_scan::dim_slices>::type;
1151 std::conditional_t<m, sequence<slice_size / slice_length>, sequence<slice_size>>,
1152 typename old_scan::remaining_slice_sizes>::type;
1153
1154 // the first idx that sliced length not equal to original length
1155 static constexpr index_t _flag =
1156 slice_length != x && remaining_slice_sizes{}.front().value == 1;
1157 static constexpr index_t _split_flag = std::conditional_t<m, number<_flag>, number<0>>::value;
1158 static constexpr index_t _split_idx =
1159 std::conditional_t<_split_flag, number<id>, number<0>>::value;
1160
1161 static constexpr index_t split_flag = _split_flag || old_scan::split_flag;
1162 static constexpr index_t split_idx = std::
1163 conditional_t<old_scan::split_flag, number<old_scan::split_idx>, number<_split_idx>>::value;
1164};
1165
1166template <index_t x, index_t m, index_t id, index_t SliceSize>
1168{
1169 static constexpr auto slice_size = SliceSize;
1170 static constexpr auto slice_length =
1171 std::conditional_t<m, number<gcd(x, slice_size)>, number<x>>::value;
1172
1176 std::conditional_t<m, sequence<slice_size / slice_length>, sequence<slice_size>>;
1177
1178 // the first idx that sliced length not equal to original length
1179 static constexpr index_t _flag =
1180 slice_length != x && remaining_slice_sizes{}.front().value == 1;
1181 static constexpr index_t split_flag = std::conditional_t<m, number<_flag>, number<0>>::value;
1182 static constexpr index_t split_idx =
1183 std::conditional_t<split_flag, number<id>, number<0>>::value;
1184};
1185} // namespace impl
1186
1187// clang-format off
1188// input a sequence(with optional mask), and the SliceSize : size per slice
1189// output the sequence each slice, and number of slices
1190// the length count for slice size is from right to left(reverse slice)
1191// or we can say, find the greatest common divider(gcd) from right to left, for the slice length
1192//
1193// e.g. <2, 8, 4>, slice length = 16
1194// step-1: we take the right most <*, *, 4>, remaining 16/4=4
1195// step-2: we only need 4 out of 8, of the midden dim, hence <*, 4, 4>
1196// step-3: since nonthing remain, so the first dim we only need 1, hence<1, 4, 4>
1197// => we got <1, 4, 4> as length for each slice
1198// => total number of slice = <2, 8, 4> / <1, 4, 4> = <2, 2, 1>
1199//
1200// e.g. <2, 1, 4, 2>, 8 -> lengths:<1, 1, 4, 2> , nums: <2, 1, 1, 1> : 2 slices , slice_idx: 0
1201// <4, 2, 4, 1, 2>, 4 -> lengths:<1, 1, 2, 1, 2> , nums: <4, 2, 2, 1, 1> : 16 slices , slice_idx: 2
1202// <4, 2, 4, 1, 6>, 4 -> lengths:<1, 1, 2, 1, 2> , nums: <4, 2, 2, 1, 3> : 48 slices , slice_idx: 2
1203// <4, 2, 5, 1, 2>, 10 -> lengths:<1, 1, 5, 1, 2> , nums: <4, 2, 1, 1, 1> : 8 slices , slice_idx: 1
1204//
1205// <4, 2, 8>, 64 -> lengths:<4, 2, 8> , nums: <1, 1, 1> : 1 slices , slice_idx: 0
1206// <4, 2, 8>, 32 -> lengths:<2, 2, 8> , nums: <2, 1, 1> : 2 slices , slice_idx: 0
1207// <4, 2, 8>, 16 -> lengths:<1, 2, 8> , nums: <4, 1, 1> : 4 slices , slice_idx: 0
1208// <4, 2, 8>, 8 -> lengths:<1, 1, 8> , nums: <4, 2, 1> : 8 slices , slice_idx: 1
1209// <4, 2, 8>, 4 -> lengths:<1, 1, 4> , nums: <4, 2, 2> : 16 slices , slice_idx: 2
1210// <4, 2, 8>, 2 -> lengths:<1, 1, 2> , nums: <4, 2, 4> : 32 slices , slice_idx: 2
1211// <4, 2, 8>, 1 -> lengths:<1, 1, 1> , nums: <4, 2, 8> : 64 slices , slice_idx: 2
1212//
1213// <4, 2, 1, 4, 2> / 4 ->
1214// mask:<1, 1, 1, 0, 1>, -> lengths:<1, 2, 1, 4, 2> , nums: <4, 1, 1, 1, 1> : 8 slices , slice_idx: 0
1215//
1216// return tuple<slice_lengths, slice_nums, slice_index>, slice_index is at which index will start
1217// have split slices (right -> left)
1218// or the first index (right -> left) that sliced length is different from the original length
1219// clang-format on
1220template <typename Seq,
1221 index_t SliceSize,
1222 typename Mask = typename uniform_sequence_gen<Seq::size(), 1>::type>
1223constexpr auto reverse_slice_sequence(Seq,
1225 Mask = typename uniform_sequence_gen<Seq::size(), 1>::type{})
1226{
1227 static_assert(Seq::size() == Mask::size());
1228 static_assert(SliceSize != 0, "slice size zero is invalid");
1229 static_assert(container_reduce(pick_sequence_elements_by_mask(Seq{}, Mask{}), multiplies{}, 1) %
1230 SliceSize ==
1231 0,
1232 "slice size can't evenly divide input sizes");
1233 using sliced_type =
1235 Mask,
1236 typename arithmetic_sequence_gen<0, Seq::size(), 1>::type,
1237 SliceSize>;
1238 static_assert(sliced_type::remaining_slice_sizes::front().value == 1,
1239 "can not evenly divide this sequence, please check");
1240 return make_tuple(typename sliced_type::dim_lengths{},
1241 typename sliced_type::dim_slices{},
1243}
1244
1245template <typename Seq,
1246 index_t SliceSize,
1247 typename Mask = typename uniform_sequence_gen<Seq::size(), 1>::type>
1248constexpr auto
1249slice_sequence(Seq, number<SliceSize>, Mask = typename uniform_sequence_gen<Seq::size(), 1>::type{})
1250{
1251 constexpr auto r =
1252 reverse_slice_sequence(Seq{}.reverse(), number<SliceSize>{}, Mask{}.reverse());
1253 return make_tuple(r[number<0>{}].reverse(),
1254 r[number<1>{}].reverse(),
1255 number<Seq::size() - r[number<2>{}] - 1>{});
1256}
1257
1258} // namespace ck_tile
#define CK_TILE_HOST_DEVICE
Definition config.hpp:42
GenericValue< UTF8<> > Value
GenericValue with UTF8 encoding.
Definition document.h:3124
Definition tile/core/arch/amd_buffer_addressing.hpp:110
__type_pack_element< I, Ts... > at_index_t
Definition tile/core/container/sequence.hpp:40
Definition tile/core/algorithm/cluster_descriptor.hpp:13
remove_cv_t< std::remove_reference_t< T > > remove_cvref_t
Definition type_traits.hpp:21
CK_TILE_HOST_DEVICE constexpr auto make_sequence(number< Is >...)
Definition tile/core/container/sequence.hpp:1029
CK_TILE_HOST_DEVICE constexpr auto operator*(const multi_index< NSize > &a, const T &b)
Definition tile/core/container/multi_index.hpp:75
CK_TILE_HOST_DEVICE constexpr auto container_reduce(const Container &x, Reduce reduce, Init init, number< IBegin >=number< 0 >{}, number< IEnd >=number< Container::size()>{}, number< IStep >=number< 1 >{})
Definition tile/core/container/container_helper.hpp:198
CK_TILE_HOST_DEVICE constexpr auto pick_sequence_elements_by_mask(Seq, Mask)
Definition tile/core/container/sequence.hpp:945
CK_TILE_HOST_DEVICE constexpr auto generate_sequence_v2(F &&f, number< N >)
Definition tile/core/container/sequence.hpp:1045
CK_TILE_HOST_DEVICE constexpr auto transform_sequences(F f, sequence< Xs... >)
Definition tile/core/container/sequence.hpp:832
CK_TILE_HOST_DEVICE constexpr auto reverse_exclusive_scan_sequence(Seq, Reduce, number< Init >)
Definition tile/core/container/sequence.hpp:863
CK_TILE_HOST_DEVICE constexpr bool sequence_any_of(Seq, F f)
Definition tile/core/container/sequence.hpp:996
CK_TILE_HOST_DEVICE constexpr auto operator+(const multi_index< NSize > &a, const T &b)
Definition tile/core/container/multi_index.hpp:55
constexpr auto reverse_slice_sequence(Seq, number< SliceSize >, Mask=typename uniform_sequence_gen< Seq::size(), 1 >::type{})
Definition tile/core/container/sequence.hpp:1223
typename __make_integer_seq< impl::__integer_sequence, index_t, N >::seq_type make_index_sequence
Definition tile/core/container/sequence.hpp:230
CK_TILE_HOST_DEVICE constexpr auto sequence_pop_back(Seq)
Definition tile/core/container/sequence.hpp:819
CK_TILE_HOST_DEVICE constexpr auto operator-(const multi_index< NSize > &a, const T &b)
Definition tile/core/container/multi_index.hpp:65
CK_TILE_HOST_DEVICE constexpr auto generate_array(F &&f, number< N >)
Definition tile/core/container/sequence.hpp:1115
constexpr auto exclusive_scan_sequence(Seq, Reduce, number< Init >)
Definition tile/core/container/sequence.hpp:901
CK_TILE_HOST_DEVICE constexpr auto merge_sequences(Seqs...)
Definition tile/core/container/sequence.hpp:826
constant< v > number
Definition tile/core/numeric/integral_constant.hpp:37
CK_TILE_HOST_DEVICE constexpr auto pick_sequence_elements_by_ids(Seq, sequence< Is... >)
Definition tile/core/container/sequence.hpp:916
CK_TILE_HOST_DEVICE constexpr index_t gcd(index_t x, index_t y)
Definition tile/core/numeric/math.hpp:268
CK_TILE_HOST_DEVICE constexpr auto generate_sequence(F, number< N >)
Definition tile/core/container/sequence.hpp:1037
CK_TILE_HOST_DEVICE constexpr auto sequence_pop_front(sequence< I, Is... >)
Definition tile/core/container/sequence.hpp:813
CK_TILE_HOST_DEVICE constexpr auto modify_sequence_elements_by_ids(Seq, Values, Ids)
Definition tile/core/container/sequence.hpp:972
CK_TILE_HOST_DEVICE constexpr auto to_sequence(tuple< number< Is >... >)
Definition tile/core/container/sequence.hpp:1055
CK_TILE_HOST_DEVICE constexpr auto unpack(F &&f, X &&x)
Definition tile/core/utility/functional.hpp:200
CK_TILE_HOST_DEVICE constexpr bool sequence_all_of(Seq, F f)
Definition tile/core/container/sequence.hpp:1010
CK_TILE_HOST_DEVICE constexpr auto operator/(sequence< Xs... >, sequence< Ys... >)
Definition tile/core/container/sequence.hpp:737
CK_TILE_HOST_DEVICE constexpr auto reverse_inclusive_scan_sequence(Seq, Reduce, number< Init >)
Definition tile/core/container/sequence.hpp:857
CK_TILE_HOST_DEVICE constexpr auto histogram_sorted_sequence(SeqSortedSamples, sequence< r, rs... >)
Definition tile/core/container/sequence.hpp:1102
CK_TILE_HOST_DEVICE constexpr auto inclusive_scan_sequence(Seq, Reduce, number< Init >)
Definition tile/core/container/sequence.hpp:870
typename sequence_merge< Seqs... >::type sequence_merge_t
Definition tile/core/container/sequence.hpp:1023
constexpr auto slice_sequence(Seq, number< SliceSize >, Mask=typename uniform_sequence_gen< Seq::size(), 1 >::type{})
Definition tile/core/container/sequence.hpp:1249
typename uniform_sequence_gen< NSize, I >::type uniform_sequence_gen_t
Definition tile/core/container/sequence.hpp:1026
int32_t index_t
Definition integer.hpp:9
CK_TILE_HOST_DEVICE constexpr bool operator==(const array< T, Size > &a, const array< T, Size > &b)
Definition tile/core/container/array.hpp:263
CK_TILE_HOST_DEVICE constexpr auto operator%(sequence< Xs... >, sequence< Ys... >)
Definition tile/core/container/sequence.hpp:745
CK_TILE_HOST_DEVICE constexpr index_t reduce_on_sequence(Seq, Reduce f, number< Init >)
Definition tile/core/container/sequence.hpp:982
CK_TILE_HOST_DEVICE constexpr auto make_tuple(Xs &&... xs)
Definition tile/core/container/tuple.hpp:360
constexpr auto prefix_sum_sequence(Seq)
Definition tile/core/container/sequence.hpp:908
CK_TILE_HOST_DEVICE constexpr bool operator!=(const array< T, Size > &a, const array< T, Size > &b)
Definition tile/core/container/array.hpp:280
const GenericPointer< typename T::ValueType > T2 value
Definition pointer.h:1697
Definition reduce2d_kernel.hpp:20
Definition tile/core/container/sequence.hpp:289
CK_TILE_HOST_DEVICE constexpr index_t operator()(index_t i) const
Definition tile/core/container/sequence.hpp:290
make_index_sequence< IEnd > type
Definition tile/core/container/sequence.hpp:308
Definition tile/core/container/sequence.hpp:287
static constexpr bool kHasContent
Definition tile/core/container/sequence.hpp:299
typename std::conditional< kHasContent, type0, type1 >::type type
Definition tile/core/container/sequence.hpp:302
typename sequence_gen<(IEnd - IBegin)/Increment, F >::type type0
Definition tile/core/container/sequence.hpp:296
sequence<> type1
Definition tile/core/container/sequence.hpp:297
A fixed-size array container similar to std::array with additional utilities.
Definition tile/core/container/array.hpp:43
Definition tile/core/container/sequence.hpp:955
typename modify_sequence_elements_by_ids_impl< new_work_seq, decltype(RemainValues::pop_front()), decltype(RemainIds::pop_front())>::type type
Definition tile/core/container/sequence.hpp:958
decltype(WorkSeq::modify(RemainIds::front(), RemainValues::front())) new_work_seq
Definition tile/core/container/sequence.hpp:956
Definition tile/core/container/sequence.hpp:925
typename std::conditional< RemainMask::front(), decltype(WorkSeq::push_back(RemainSeq::front())), WorkSeq >::type new_work_seq
Definition tile/core/container/sequence.hpp:926
typename pick_sequence_elements_by_mask_impl< new_work_seq, decltype(RemainSeq::pop_front()), decltype(RemainMask::pop_front())>::type type
Definition tile/core/container/sequence.hpp:930
constexpr auto operator()(Histogram &h)
Definition tile/core/container/sequence.hpp:1068
constexpr auto operator()(Histogram &h)
Definition tile/core/container/sequence.hpp:1087
Definition tile/core/container/sequence.hpp:1062
sequence< Ints... > seq_type
Definition tile/core/container/sequence.hpp:224
Definition tile/core/container/sequence.hpp:219
typename sequence_merge< sequence< x/slice_length >, typename old_scan::dim_slices >::type dim_slices
Definition tile/core/container/sequence.hpp:1148
typename sequence_merge< std::conditional_t< m, sequence< slice_size/slice_length >, sequence< slice_size > >, typename old_scan::remaining_slice_sizes >::type remaining_slice_sizes
Definition tile/core/container/sequence.hpp:1150
typename sequence_merge< sequence< slice_length >, typename old_scan::dim_lengths >::type dim_lengths
Definition tile/core/container/sequence.hpp:1146
reverse_slice_sequence_impl< sequence< xs... >, sequence< ms... >, sequence< ids... >, SliceSize > old_scan
Definition tile/core/container/sequence.hpp:1139
sequence< slice_length > dim_lengths
Definition tile/core/container/sequence.hpp:1173
static constexpr index_t split_idx
Definition tile/core/container/sequence.hpp:1182
std::conditional_t< m, sequence< slice_size/slice_length >, sequence< slice_size > > remaining_slice_sizes
Definition tile/core/container/sequence.hpp:1175
sequence< x/slice_length > dim_slices
Definition tile/core/container/sequence.hpp:1174
static constexpr index_t split_flag
Definition tile/core/container/sequence.hpp:1181
static constexpr auto slice_length
Definition tile/core/container/sequence.hpp:1170
static constexpr index_t _flag
Definition tile/core/container/sequence.hpp:1179
static constexpr auto slice_size
Definition tile/core/container/sequence.hpp:1169
Definition tile/core/container/sequence.hpp:1125
impl::at_index_t< I, constant< Ns >... > element
Definition tile/core/container/sequence.hpp:396
sequence< element<(sizeof...(Ns) - 1 - Ids)>::value... > type
Definition tile/core/container/sequence.hpp:397
Definition tile/core/container/sequence.hpp:390
Definition tile/core/container/sequence.hpp:670
Definition tile/core/numeric/math.hpp:98
Definition tile/core/numeric/math.hpp:50
typename sequence_exclusive_scan< old_scan, sequence< Ys... >, Reduce >::type type
Definition tile/core/container/sequence.hpp:885
typename sequence_merge< sequence< Xs... >, sequence< Reduce{}(Y, sequence< Xs... >{}.back())> >::type old_scan
Definition tile/core/container/sequence.hpp:883
sequence< Xs... > type
Definition tile/core/container/sequence.hpp:891
sequence< Xs... > type
Definition tile/core/container/sequence.hpp:897
Definition tile/core/container/sequence.hpp:878
sequence<> type
Definition tile/core/container/sequence.hpp:278
sequence< Is > type
Definition tile/core/container/sequence.hpp:272
static constexpr index_t Is
Definition tile/core/container/sequence.hpp:271
Definition tile/core/container/sequence.hpp:258
static constexpr index_t NRemainLeft
Definition tile/core/container/sequence.hpp:259
typename sequence_merge< typename sequence_gen_impl< IBegin, NRemainLeft, G >::type, typename sequence_gen_impl< IMiddle, NRemainRight, G >::type >::type type
Definition tile/core/container/sequence.hpp:263
static constexpr index_t NRemainRight
Definition tile/core/container/sequence.hpp:260
static constexpr index_t IMiddle
Definition tile/core/container/sequence.hpp:261
Definition tile/core/container/sequence.hpp:255
typename sequence_gen_impl< 0, NSize, F >::type type
Definition tile/core/container/sequence.hpp:281
WorkingY2X type
Definition tile/core/container/sequence.hpp:690
Definition tile/core/container/sequence.hpp:678
static constexpr auto new_y2x
Definition tile/core/container/sequence.hpp:679
typename sequence_map_inverse_impl< X2Y, decltype(new_y2x), XBegin+1, XRemain - 1 >:: type type
Definition tile/core/container/sequence.hpp:682
Definition tile/core/container/sequence.hpp:675
typename sequence_map_inverse_impl< SeqMap, typename uniform_sequence_gen< SeqMap::size(), 0 >::type, 0, SeqMap::size()>::type type
Definition tile/core/container/sequence.hpp:693
Seq type
Definition tile/core/container/sequence.hpp:249
sequence< Xs..., Ys... > type
Definition tile/core/container/sequence.hpp:243
Definition tile/core/container/sequence.hpp:236
typename sequence_merge< Seq, typename sequence_merge< Seqs... >::type >::type type
Definition tile/core/container/sequence.hpp:237
Seq type
Definition tile/core/container/sequence.hpp:428
sequence< Reduce{}(Xs, Ys)... > type
Definition tile/core/container/sequence.hpp:422
Definition tile/core/container/sequence.hpp:413
typename sequence_reduce< Reduce, Seq, typename sequence_reduce< Reduce, Seqs... >::type >::type type
Definition tile/core/container/sequence.hpp:414
typename sequence_reverse_inclusive_scan< sequence< Is... >, Reduce, Init >::type old_scan
Definition tile/core/container/sequence.hpp:330
static constexpr index_t new_reduce
Definition tile/core/container/sequence.hpp:332
typename sequence_merge< sequence< new_reduce >, old_scan >::type type
Definition tile/core/container/sequence.hpp:334
sequence< Reduce{}(I, Init)> type
Definition tile/core/container/sequence.hpp:340
sequence<> type
Definition tile/core/container/sequence.hpp:346
Definition tile/core/container/sequence.hpp:325
Definition tile/core/container/sequence.hpp:23
typename sequence_merge< MergedIds, LeftIds >::type merged_ids
Definition tile/core/container/sequence.hpp:489
typename sequence_merge< MergedValues, LeftValues >::type merged_values
Definition tile/core/container/sequence.hpp:488
typename sequence_merge< MergedIds, RightIds >::type merged_ids
Definition tile/core/container/sequence.hpp:506
typename sequence_merge< MergedValues, RightValues >::type merged_values
Definition tile/core/container/sequence.hpp:505
Definition tile/core/container/sequence.hpp:443
typename std::conditional< choose_left, RightIds, decltype(RightIds::pop_front())>::type new_right_ids
Definition tile/core/container/sequence.hpp:460
decltype(MergedIds::push_back(number< chosen_id >{})) new_merged_ids
Definition tile/core/container/sequence.hpp:451
decltype(MergedValues::push_back(number< chosen_value >{})) new_merged_values
Definition tile/core/container/sequence.hpp:450
sorted_sequence_merge_impl< new_left_values, new_left_ids, new_right_values, new_right_ids, new_merged_values, new_merged_ids, Comp > merge
Definition tile/core/container/sequence.hpp:463
typename std:: conditional< choose_left, RightValues, decltype(RightValues::pop_front())>::type new_right_values
Definition tile/core/container/sequence.hpp:458
typename std:: conditional< choose_left, decltype(LeftValues::pop_front()), LeftValues >::type new_left_values
Definition tile/core/container/sequence.hpp:453
typename std::conditional< choose_left, decltype(LeftIds::pop_front()), LeftIds >::type new_left_ids
Definition tile/core/container/sequence.hpp:455
Definition tile/core/container/sequence.hpp:515
typename merge::merged_values merged_values
Definition tile/core/container/sequence.hpp:524
typename merge::merged_ids merged_ids
Definition tile/core/container/sequence.hpp:525
sorted_sequence_merge_impl< LeftValues, LeftIds, RightValues, RightIds, sequence<>, sequence<>, Comp > merge
Definition tile/core/container/sequence.hpp:516
sequence< Value > sorted_values
Definition tile/core/container/sequence.hpp:569
sequence< Id > sorted_ids
Definition tile/core/container/sequence.hpp:570
static constexpr bool choose_x
Definition tile/core/container/sequence.hpp:558
typename std:: conditional< choose_x, sequence< ValueX, ValueY >, sequence< ValueY, ValueX > >::type sorted_values
Definition tile/core/container/sequence.hpp:560
typename std::conditional< choose_x, sequence< IdX, IdY >, sequence< IdY, IdX > >::type sorted_ids
Definition tile/core/container/sequence.hpp:562
sequence<> sorted_ids
Definition tile/core/container/sequence.hpp:577
sequence<> sorted_values
Definition tile/core/container/sequence.hpp:576
Definition tile/core/container/sequence.hpp:434
typename right_sort::sorted_values right_sorted_values
Definition tile/core/container/sequence.hpp:542
typename merged_sorted::merged_values sorted_values
Definition tile/core/container/sequence.hpp:551
typename right_sort::sorted_ids right_sorted_ids
Definition tile/core/container/sequence.hpp:543
sequence_split< Values, nsize/2 > split_unsorted_values
Definition tile/core/container/sequence.hpp:530
typename split_unsorted_values::right_type right_unsorted_values
Definition tile/core/container/sequence.hpp:539
sequence_sort_impl< left_unsorted_values, left_unsorted_ids, Compare > left_sort
Definition tile/core/container/sequence.hpp:535
typename split_unsorted_ids::left_type left_unsorted_ids
Definition tile/core/container/sequence.hpp:534
sequence_sort_impl< right_unsorted_values, right_unsorted_ids, Compare > right_sort
Definition tile/core/container/sequence.hpp:541
sequence_split< Ids, nsize/2 > split_unsorted_ids
Definition tile/core/container/sequence.hpp:531
typename split_unsorted_ids::right_type right_unsorted_ids
Definition tile/core/container/sequence.hpp:540
static constexpr index_t nsize
Definition tile/core/container/sequence.hpp:528
typename left_sort::sorted_values left_sorted_values
Definition tile/core/container/sequence.hpp:536
typename left_sort::sorted_ids left_sorted_ids
Definition tile/core/container/sequence.hpp:537
sorted_sequence_merge< left_sorted_values, left_sorted_ids, right_sorted_values, right_sorted_ids, Compare > merged_sorted
Definition tile/core/container/sequence.hpp:545
typename merged_sorted::merged_ids sorted_ids
Definition tile/core/container/sequence.hpp:552
typename split_unsorted_values::left_type left_unsorted_values
Definition tile/core/container/sequence.hpp:533
Definition tile/core/container/sequence.hpp:582
typename sort::sorted_values type
Definition tile/core/container/sequence.hpp:587
typename arithmetic_sequence_gen< 0, Values::size(), 1 >::type unsorted_ids
Definition tile/core/container/sequence.hpp:583
sequence_sort_impl< Values, unsorted_ids, Compare > sort
Definition tile/core/container/sequence.hpp:584
typename sort::sorted_ids sorted2unsorted_map
Definition tile/core/container/sequence.hpp:588
Definition tile/core/container/sequence.hpp:352
decltype(Seq::extract(range1{})) right_type
Definition tile/core/container/sequence.hpp:359
typename arithmetic_sequence_gen< I, NSize, 1 >::type range1
Definition tile/core/container/sequence.hpp:356
typename arithmetic_sequence_gen< 0, I, 1 >::type range0
Definition tile/core/container/sequence.hpp:355
static constexpr index_t NSize
Definition tile/core/container/sequence.hpp:353
decltype(Seq::extract(range0{})) left_type
Definition tile/core/container/sequence.hpp:358
Definition tile/core/container/sequence.hpp:600
decltype(RemainValues::pop_front()) new_remain_values
Definition tile/core/container/sequence.hpp:606
sorted_sequence_uniquify_impl< new_remain_values, new_remain_ids, new_uniquified_values, new_uniquified_ids, Eq > uniquify
Definition tile/core/container/sequence.hpp:620
typename std::conditional< is_unique_value, decltype(UniquifiedValues::push_back( number< current_value >{})), UniquifiedValues >::type new_uniquified_values
Definition tile/core/container/sequence.hpp:609
decltype(RemainIds::pop_front()) new_remain_ids
Definition tile/core/container/sequence.hpp:607
typename std::conditional< is_unique_value, decltype(UniquifiedIds::push_back(number< current_id >{})), UniquifiedIds >::type new_uniquified_ids
Definition tile/core/container/sequence.hpp:615
Definition tile/core/container/sequence.hpp:644
typename uniquify::uniquified_ids uniquified_ids
Definition tile/core/container/sequence.hpp:652
sorted_sequence_uniquify_impl< decltype(SortedValues::pop_front()), decltype(SortedIds::pop_front()), sequence< SortedValues::front()>, sequence< SortedIds::front()>, Eq > uniquify
Definition tile/core/container/sequence.hpp:645
typename uniquify::uniquified_values uniquified_values
Definition tile/core/container/sequence.hpp:651
Definition tile/core/container/sequence.hpp:593
sequence_sort< Values, Less > sort
Definition tile/core/container/sequence.hpp:655
typename sort::sorted2unsorted_map sorted_ids
Definition tile/core/container/sequence.hpp:657
typename uniquify::uniquified_values type
Definition tile/core/container/sequence.hpp:662
typename uniquify::uniquified_ids sorted2unsorted_map
Definition tile/core/container/sequence.hpp:663
typename sort::type sorted_values
Definition tile/core/container/sequence.hpp:656
sorted_sequence_uniquify< sorted_values, sorted_ids, Equal > uniquify
Definition tile/core/container/sequence.hpp:659
Definition tile/core/container/sequence.hpp:49
static CK_TILE_HOST_DEVICE constexpr auto reorder_old_to_new(MapOld2New)
Definition tile/core/container/sequence.hpp:110
static CK_TILE_HOST_DEVICE constexpr auto pop_back()
Definition tile/core/container/sequence.hpp:139
index_t value_type
Definition tile/core/container/sequence.hpp:51
static CK_TILE_HOST_DEVICE constexpr auto get(number< I >)
Definition tile/core/container/sequence.hpp:64
static CK_TILE_HOST_DEVICE constexpr auto transform(F f)
Definition tile/core/container/sequence.hpp:195
static CK_TILE_HOST_DEVICE constexpr auto sum()
Definition tile/core/container/sequence.hpp:178
sequence type
Definition tile/core/container/sequence.hpp:50
static CK_TILE_HOST_DEVICE constexpr auto pop_front()
Definition tile/core/container/sequence.hpp:137
static CK_TILE_HOST_DEVICE constexpr auto back()
Definition tile/core/container/sequence.hpp:131
static CK_TILE_HOST_DEVICE constexpr auto at()
Definition tile/core/container/sequence.hpp:78
static CK_TILE_HOST_DEVICE constexpr auto at(number< I >)
Definition tile/core/container/sequence.hpp:85
static CK_TILE_HOST_DEVICE constexpr auto product()
Definition tile/core/container/sequence.hpp:179
static CK_TILE_HOST_DEVICE constexpr auto push_front(number< Xs >...)
Definition tile/core/container/sequence.hpp:148
static CK_TILE_HOST_DEVICE constexpr auto push_back(sequence< Xs... >)
Definition tile/core/container/sequence.hpp:154
static CK_TILE_HOST_DEVICE constexpr index_t size()
Definition tile/core/container/sequence.hpp:53
static CK_TILE_HOST_DEVICE constexpr index_t at(index_t I)
Definition tile/core/container/sequence.hpp:70
static CK_TILE_HOST_DEVICE constexpr bool is_static()
Definition tile/core/container/sequence.hpp:54
static CK_TILE_HOST_DEVICE constexpr auto extract(sequence< Ids... >)
Definition tile/core/container/sequence.hpp:173
static CK_TILE_HOST_DEVICE constexpr auto push_front(sequence< Xs... >)
Definition tile/core/container/sequence.hpp:142
static CK_TILE_HOST_DEVICE constexpr auto reverse()
Definition tile/core/container/sequence.hpp:120
CK_TILE_HOST_DEVICE constexpr auto operator[](I i) const
Definition tile/core/container/sequence.hpp:92
static CK_TILE_HOST_DEVICE constexpr auto get()
Definition tile/core/container/sequence.hpp:57
static CK_TILE_HOST_DEVICE constexpr auto reorder_new_to_old(sequence< IRs... >)
Definition tile/core/container/sequence.hpp:98
static CK_TILE_HOST_DEVICE constexpr auto front()
Definition tile/core/container/sequence.hpp:125
static CK_TILE_HOST_DEVICE constexpr auto push_back(number< Xs >...)
Definition tile/core/container/sequence.hpp:160
static CK_TILE_HOST_DEVICE constexpr auto modify(number< I >, number< X >)
Definition tile/core/container/sequence.hpp:183
static CK_TILE_HOST_DEVICE constexpr auto extract(number< Ids >...)
Definition tile/core/container/sequence.hpp:167
Definition tile/core/container/tuple.hpp:192
Definition tile/core/container/sequence.hpp:316
CK_TILE_HOST_DEVICE constexpr index_t operator()(index_t) const
Definition tile/core/container/sequence.hpp:317
Definition tile/core/container/sequence.hpp:314
typename sequence_gen< NSize, F >::type type
Definition tile/core/container/sequence.hpp:320
#define TO_SEQUENCE(a, n)
Definition to_sequence.hpp:10