Skip to content

Commit 75a8d7c

Browse files
committed
std::nan added,
1 parent 6754621 commit 75a8d7c

6 files changed

+382
-493
lines changed

README.md

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -165,7 +165,7 @@ This change ensures that VSCode uses the "Ninja Multi-Config" generator by defau
165165
* [stack, queue, priority_queue, deque](docs/stack_queue_priority_queue_deque.md)
166166
* [Const, Constexpr and Mutable](docs/const_constexpr_mutable.md)
167167
* [Immutable Objects](docs/immutable_objects.md)
168-
* [Data Types, Numerical Limits, Machine Epsilon, Precision](docs/primitive_data_types_numerical_limits_machine_epsilon_precision.md)
168+
* [Data Types, Numerical Limits, Machine Epsilon, Precision, std::nan](docs/primitive_data_types_numerical_limits_machine_epsilon_precision.md)
169169
* [Data Types Conversions, Casting, Type Coercion](docs/type_conversions_casting_type_coercion.md)
170170
* [Decay](docs/decay.md)
171171
* [Dynamic Memory Allocation in C](docs/dynamic_memory_allocation.md)

docs/algorithms.md

Lines changed: 89 additions & 63 deletions
Original file line numberDiff line numberDiff line change
@@ -25,74 +25,100 @@ The `<algorithm>` header in C++20 includes a wide range of functions that are es
2525
- `std::sort`: Sort elements in a range.
2626
- `std::stable_sort`: Stable sort elements.
2727
- `std::partial_sort`: Partially sort elements in a range, up to the `K'th` element.
28-
```cpp
29-
int Kth = 4;
30-
std::vector<int> arr = {5, 812, 4, 74, 68, 7, 48, 45};
31-
std::partial_sort(arr.begin(), arr.begin() + Kth, arr.end());
32-
```
33-
28+
```cpp
29+
int Kth = 4;
30+
std::vector<int> arr = {5, 812, 4, 74, 68, 7, 48, 45};
31+
std::partial_sort(arr.begin(), arr.begin() + Kth, arr.end());
32+
```
33+
- `std::partial_sort_copy`: Copies elements from an input range to an output range, Simultaneously sorts the elements copied to the output range. Only the first `n` elements of the output range are guaranteed to be sorted. is efficient for finding a specific number of smallest or largest elements without sorting the entire input range.
34+
```cpp
35+
int Kth = 4;
36+
std::vector<int> numbers = {64, 25, 12, 22, 11, 90};
37+
std::vector<int> result(Kth); // We want the 4 smallest elements
38+
39+
std::partial_sort_copy(numbers.begin(), numbers.end(), result.begin(),result.end());
40+
```
3441
- `std::nth_element`: partially sorts a range of elements. It rearranges the elements such that the element at the specified nth position is the one that would be at that position if the entire range were sorted. It is efficient for finding specific elements (like **median, kth smallest/largest**) without sorting the entire container.
35-
```cpp
36-
std::vector<int> numbers = {3, 7, 4, 9, 2, 5, 8, 1, 6};
37-
38-
// Find the median
39-
auto middle = numbers.begin() + numbers.size() / 2;
40-
std::nth_element(numbers.begin(), middle, numbers.end());
42+
```cpp
43+
std::vector<int> numbers = {3, 7, 4, 9, 2, 5, 8, 1, 6};
4144

42-
std::cout << "Median: " << *middle << std::endl;
43-
```
44-
45-
- `std::partial_sort_copy`: Copies elements from an input range to an output range, Simultaneously sorts the elements copied to the output range. Only the first `n` elements of the output range are guaranteed to be sorted.
45+
// Find the median
46+
auto middle = numbers.begin() + numbers.size() / 2;
47+
std::nth_element(numbers.begin(), middle, numbers.end());
4648

47-
**Syntax:**
48-
49-
```cpp
50-
std::partial_sort_copy(first, last, result_first, result_last);
51-
```
52-
53-
* `first` and `last`: Iterators defining the range of elements to be copied.
54-
* `result_first` and `result_last`: Iterators defining the range of elements to be copied to.
55-
56-
**Example:**
57-
58-
```cpp
59-
#include <iostream>
60-
#include <vector>
61-
#include <algorithm>
62-
63-
int main() {
64-
std::vector<int> numbers = { 64, 25, 12, 22, 11, 90 };
65-
std::vector<int> result(3); // We want the 3 smallest elements
66-
67-
std::partial_sort_copy(numbers.begin(), numbers.end(), result.begin(), result.end());
68-
69-
std::cout << "Original numbers: ";
70-
for (int num : numbers) {
71-
std::cout << num << " ";
72-
}
73-
std::cout << std::endl;
74-
75-
std::cout << "Smallest 3 numbers: ";
76-
for (int num : result) {
77-
std::cout << num << " ";
78-
}
79-
std::cout << std::endl;
80-
81-
return 0;
82-
}
83-
```
84-
85-
**Key points:**
86-
* `std::partial_sort_copy` is efficient for finding a specific number of smallest or largest elements without sorting the entire input range.
87-
* The output range must be large enough to hold at least as many elements as the number of elements you want to copy.
88-
* The elements beyond the first `n` elements in the output range are not guaranteed to be sorted.
49+
std::cout << "Median: " << *middle << std::endl;
50+
```
51+
- `std::priority_queue`: use heap for finding max/min value
52+
53+
```cpp
54+
std::priority_queue<int, std::vector<int>, std::greater<int>> q2;
55+
for (int n : {1, 8, 5, 6, 3, 4, 0, 9, 7, 2})
56+
q2.push(n);
57+
58+
```
59+
60+
using custom_comparator:
61+
62+
```cpp
63+
64+
auto comparator = [](int left, int right) {
65+
return (left ^ 1) < (right ^ 1);
66+
};
67+
68+
std::priority_queue<int, std::vector<int>, decltype(comparator)>
69+
q_custom_comparator(comparator);
70+
for (int n : {1, 8, 5, 6, 3, 4, 0, 9, 7, 2})
71+
q_custom_comparator.push(n);
72+
```
73+
74+
Here `decltype` is used to deduce the type of the comparator function (the lambda) so that it can be used as the third template argument when defining the
75+
76+
#### Why `decltype` is Needed:
77+
78+
1. **Lambda Functions Have Unique Types:**
79+
- Lambda functions in C++ have unique, unnamed types generated by the compiler. These types are not directly accessible by name, so you cannot simply specify the type of the lambda in the template parameters of `std::priority_queue`.
80+
81+
2. **Specifying the Comparator Type:**
82+
- The `std::priority_queue` requires the type of the comparator as its third template argument to define how the elements should be ordered. Since the type of a lambda is unnamed and complex, `decltype` is used to deduce and retrieve this type.
83+
84+
#### How `decltype` Works Here:
85+
86+
- **`decltype(comparator)`**:
87+
- `decltype` is used to deduce the exact type of the `comparator` lambda function. This allows `std::priority_queue` to know the type of the comparator it should use.
88+
89+
- **Initialization**:
90+
- When you initialize the `std::priority_queue`, you need to pass the `comparator` to its constructor so that it knows how to compare the elements.
91+
- Using `decltype(comparator)` allows the `std::priority_queue` to correctly store and use the lambda for comparison.
92+
93+
94+
95+
96+
using custom struct:
97+
98+
```cpp
99+
// Define the cell struct
100+
struct cell {
101+
int index;
102+
float cost;
103+
};
104+
105+
// Define a custom comparison functor
106+
struct CompareCell {
107+
bool operator()(const cell &a, const cell &b) {
108+
return a.cost > b.cost; // Min-heap: smallest cost has highest priority
109+
}
110+
};
111+
```
112+
In your main:
113+
- The first parameter is the type of elements stored (cell).
114+
- The second parameter is the underlying container type (std::vector<cell>).
115+
- The third parameter is the comparison functor (CompareCell).
116+
117+
```cpp
118+
std::priority_queue<cell, std::vector<cell>, CompareCell> pq;
119+
```
89120

90-
**Additional notes:**
91-
* You can use custom comparison functions with `std::partial_sort_copy` to sort elements based on different criteria.
92-
* For more complex sorting scenarios, consider using `std::stable_partition` or writing custom sorting algorithms.
93121

94-
By understanding `std::partial_sort_copy`, you can effectively handle situations where you need to extract a sorted subset of elements from a larger unsorted collection without modifying the original data.
95-
96122

97123
5. **Binary Search Operations (on sorted ranges):**
98124
- `std::lower_bound` and `std::upper_bound`: Find bounds in a sorted range.

0 commit comments

Comments
 (0)