200 lines
5.8 KiB
Markdown
200 lines
5.8 KiB
Markdown
# Permutations Exercise - Simple Explanation 🔄
|
||
|
||
## What is a Permutation? 🤔
|
||
|
||
Imagine you have some letters, like the letters in your name. A **permutation** is just a fancy word for "all the different ways you can arrange those letters."
|
||
|
||
Think of it like this:
|
||
- If you have the letters **A** and **B**, you can arrange them as **AB** or **BA**
|
||
- If you have **A**, **B**, and **C**, you can make **ABC**, **ACB**, **BAC**, **BCA**, **CAB**, **CBA**
|
||
|
||
It's like having alphabet blocks and seeing how many different words you can spell by changing the order!
|
||
|
||
## The Challenge 🎯
|
||
|
||
Your mission is to write a program that:
|
||
1. Takes a word (like "abc")
|
||
2. Shows ALL possible ways to rearrange the letters
|
||
3. Shows them in **alphabetical order** (like in a dictionary)
|
||
|
||
## Real Examples 📝
|
||
|
||
Let's see what our program does:
|
||
|
||
### Example 1: Single Letter
|
||
```bash
|
||
./permutations a
|
||
```
|
||
**Output:** `a`
|
||
|
||
*Why?* There's only one letter, so there's only one way to arrange it!
|
||
|
||
### Example 2: Two Letters
|
||
```bash
|
||
./permutations ab
|
||
```
|
||
**Output:**
|
||
```
|
||
ab
|
||
ba
|
||
```
|
||
|
||
*Why?* We can put 'a' first or 'b' first. That's it!
|
||
|
||
### Example 3: Three Letters
|
||
```bash
|
||
./permutations abc
|
||
```
|
||
**Output:**
|
||
```
|
||
abc
|
||
acb
|
||
bac
|
||
bca
|
||
cab
|
||
cba
|
||
```
|
||
|
||
*Why?* Think of it step by step:
|
||
- Start with 'a': we can make **abc** and **acb**
|
||
- Start with 'b': we can make **bac** and **bca**
|
||
- Start with 'c': we can make **cab** and **cba**
|
||
|
||
## How Our Code Works 🛠️
|
||
|
||
### Step 1: Getting Ready
|
||
```c
|
||
// We take the word you give us
|
||
char *str = argv[1]; // This is your word like "abc"
|
||
|
||
// We make a copy so we don't mess up the original
|
||
copy = malloc(sizeof(char) * (len + 1));
|
||
```
|
||
|
||
### Step 2: Sorting First (The Secret Sauce! ✨)
|
||
```c
|
||
ft_sort_string(copy); // This puts letters in order: "cba" becomes "abc"
|
||
```
|
||
|
||
**Why do we sort first?**
|
||
- If someone gives us "cba", we sort it to "abc" first
|
||
- This way, we always start with letters in alphabetical order
|
||
- Then when we make all arrangements, they come out in the right order!
|
||
|
||
### Step 3: The Magic Swapping Function
|
||
```c
|
||
void ft_swap(char *a, char *b)
|
||
{
|
||
char temp = *a; // Remember the first letter
|
||
*a = *b; // Put the second letter in first position
|
||
*b = temp; // Put the first letter in second position
|
||
}
|
||
```
|
||
|
||
**What's swapping?** It's like switching two cards in your hand:
|
||
- You have cards **A** and **B**
|
||
- After swapping, you have **B** and **A**
|
||
|
||
### Step 4: The Next Permutation Magic 🪄
|
||
```c
|
||
int next_permutation(char *str, int len)
|
||
{
|
||
int i = len - 2;
|
||
while (i >= 0 && str[i] >= str[i + 1]) // Find rightmost character smaller than next
|
||
i--;
|
||
if (i < 0)
|
||
return (0); // No more permutations
|
||
|
||
int j = len - 1;
|
||
while (str[j] <= str[i]) // Find rightmost character greater than str[i]
|
||
j--;
|
||
ft_swap(&str[i], &str[j]); // Swap them
|
||
ft_reverse(str, i + 1, len - 1); // Reverse the suffix
|
||
return (1); // Successfully generated next permutation
|
||
}
|
||
```
|
||
|
||
**How does this work?** Think of it like counting in a special way:
|
||
1. **Find** the rightmost place where we can "increment" (make it bigger)
|
||
2. **Swap** with the next bigger character available
|
||
3. **Reverse** everything after that position to get the smallest arrangement
|
||
4. **Repeat** until no more permutations exist
|
||
|
||
It's like a smart odometer that counts through all possible letter arrangements in perfect alphabetical order!
|
||
|
||
### Step 5: The Main Loop 🔄
|
||
```c
|
||
ft_sort_string(copy); // Start with alphabetically first arrangement
|
||
puts(copy); // Print the first permutation
|
||
while (next_permutation(copy, len)) // While there are more permutations
|
||
puts(copy); // Print each one
|
||
```
|
||
|
||
**How does this work?**
|
||
1. **Start** with the smallest (first) arrangement: "abc"
|
||
2. **Print** it
|
||
3. **Generate** the next alphabetical arrangement using `next_permutation`
|
||
4. **Print** it
|
||
5. **Repeat** until `next_permutation` says "no more!"
|
||
|
||
It's like flipping through a dictionary - each page (permutation) comes in perfect alphabetical order!
|
||
|
||
## Why This Approach is Cool 😎
|
||
|
||
### The Step-by-Step Process 📋
|
||
When we have "abc", our program works like this:
|
||
|
||
```
|
||
1. Start: abc (sorted, print it!)
|
||
2. Next: acb (swap 'b' and 'c', print it!)
|
||
3. Next: bac (find next in alphabetical order, print it!)
|
||
4. Next: bca (continue the pattern, print it!)
|
||
5. Next: cab (keep going, print it!)
|
||
6. Next: cba (last one, print it!)
|
||
7. Done: No more permutations possible
|
||
```
|
||
|
||
**The Magic:** Each step finds the next arrangement that would come after the current one in a dictionary! It's like having a super-smart assistant who knows exactly what comes next alphabetically.
|
||
|
||
### Memory Management 🧠
|
||
```c
|
||
copy = malloc(sizeof(char) * (len + 1)); // Ask for memory
|
||
// ... do our work ...
|
||
free(copy); // Give memory back when done
|
||
```
|
||
|
||
We're polite programmers - we clean up after ourselves!
|
||
|
||
### Error Handling 🛡️
|
||
```c
|
||
if (argc != 2) // Did you give us exactly one word?
|
||
return (1); // If not, we quit
|
||
|
||
if (!copy) // Did we get the memory we asked for?
|
||
return (1); // If not, we quit safely
|
||
```
|
||
|
||
We check if things went wrong and handle it gracefully.
|
||
|
||
## Fun Facts! 🎉
|
||
|
||
- With 1 letter: **1** permutation
|
||
- With 2 letters: **2** permutations
|
||
- With 3 letters: **6** permutations
|
||
- With 4 letters: **24** permutations
|
||
- With 5 letters: **120** permutations
|
||
|
||
**Pattern?** For n letters, you get n × (n-1) × (n-2) × ... × 1 permutations!
|
||
|
||
## Try It Yourself! 🚀
|
||
|
||
1. Compile the program: `gcc -Wall -Wextra -Werror permutations.c -o permutations`
|
||
2. Try it with your name: `./permutations john`
|
||
3. Try it with short words: `./permutations cat`
|
||
4. See how the results are always in alphabetical order!
|
||
|
||
Remember: The computer is doing exactly what we told it to do, step by step, just like following a recipe! 👨🍳
|
||
|
||
---
|
||
|
||
*Made with ❤️ for curious minds who want to understand how permutations work!* |