From b028290107064e478a0e96c9ff513f7717494911 Mon Sep 17 00:00:00 2001 From: Miloslav Ciz Date: Mon, 4 Apr 2022 21:04:54 +0200 Subject: [PATCH] Update --- c_tutorial.md | 65 +++++++++++++++++++++++++++++++++++++++++++++------ fsf.md | 3 +++ gnu.md | 10 ++++++++ main.md | 2 ++ rms.md | 6 +++-- 5 files changed, 77 insertions(+), 9 deletions(-) create mode 100644 fsf.md create mode 100644 gnu.md diff --git a/c_tutorial.md b/c_tutorial.md index b020b1b..70f399a 100644 --- a/c_tutorial.md +++ b/c_tutorial.md @@ -1,6 +1,8 @@ # C Tutorial -This is a relatively quick WIP [C](c.md) tutorial. +{ Still a work in progress. ~drummyfish } + +This is a relatively quick [C](c.md) tutorial. You should probably know at least the completely basic ideas of programming before reading this (what's a [programming language](programming_language.md), [source code](source_code.md), [command line](cli.md) etc.). If you're as far as already knowing another language, this should be pretty easy to understand. @@ -1401,14 +1403,14 @@ Now that know about pointers, we can finally completely explain the functions fr ## Files -Now we'll take a look at how we can read and write from/to file on the computer disk which allows us to store information permanently or potentially process data such as images or audio. Files aren't so difficult. +Now we'll take a look at how we can read and write from/to files on the computer disk which enables us to store information permanently or potentially process data such as images or audio. Files aren't so difficult. -We work with files through functions provide in the *stdio* library (so it has to be included). We distinguish two types of files: +We work with files through functions provided in the *stdio* library (so it has to be included). We distinguish two types of files: - **text files**: Contain text, are human readable. - **binary files**: Contain binary data, aren't human readable, are more efficient but also more prone to corruption. -From programmer's point of view there's actually not a huge difference between the two, they're both just sequences of characters or bytes (which are kind of almost the same). Text files are a little more abstract, they handle potentially different format of newlines etc. The main thing for us is that we'll use slightly different function for each type. +From programmer's point of view there's actually not a huge difference between the two, they're both just sequences of characters or bytes (which are kind of almost the same). Text files are a little more abstract, they handle potentially different format of newlines etc. The main thing for us is that we'll use slightly different functions for each type. There is a special data type for file called `FILE` (we'll be using a pointer to it). Whatever file we work with, we need to firstly open it with the function `fopen` and when we're done with it, we need to close it with a function `fclose`. @@ -1434,7 +1436,7 @@ int main(void) When run, the program should create a new file named *test.txt* in the same directory we're in and in it you should find the text `Hello file.`. `FILE *textFile` creates a new variable `textFile` which is a pointer to the `FILE` data type. We are using a pointer simply because the standard library is designed this way, its functions work with pointers (it can be more efficient). `fopen("test.txt","w");` attempts to open the file *test.txt* in text mode for writing -- it returns a pointer that represents the opened file. The mode, i.e. text/binary, read/write etc., is specified by the second argument: `"w"`; *w* simply specifies *write* and the text mode is implicit (it doesn't have to be specified). `if (textFile != NULL)` checks if the file has been successfully opened; the function `fopen` returns `NULL` (the value of "point to nothing" pointers) if there was an error with opening the file (such as that the file doesn't exist). On success we write text to the file with a function `fprintf` -- it's basically the same as `printf` but works on files, so it's first parameter is always a pointer to a file to which it should write. You can of course also print numbers and anything that `printf` can with this function. Finally we mustn't forget to close the file at the end with `fclose`! -Now let's write another program that read the file we've just created and writes its content out in the command line: +Now let's write another program that reads the file we've just created and writes its content out in the command line: ``` #include @@ -1459,7 +1461,7 @@ int main(void) } ``` -Notice that in `fopen` we nowe specify `"w"` (write) as a mode. Again, we check if the file has been opened successfully (`if (textFile != NULL)`). If so, we use a `while` loop to read and print all characters from the file until we encounter the end of file. The reading of file characters is done with the `fscanf` function inside the loop's condition -- there's nothing preventing us from doing this. `fscanf` again works the same as `scanf` (so it can read other types than only `char`s), just on files (its first argument is the file to read from). On encountering end of file `fscanf` returns a special value `EOF` (which is macro constant defined in the standard library). Again, we must close the file at the end with `fclose`. +Notice that in `fopen` we now specify `"w"` (write) as a mode. Again, we check if the file has been opened successfully (`if (textFile != NULL)`). If so, we use a `while` loop to read and print all characters from the file until we encounter the end of file. The reading of file characters is done with the `fscanf` function inside the loop's condition -- there's nothing preventing us from doing this. `fscanf` again works the same as `scanf` (so it can read other types than only `char`s), just on files (its first argument is the file to read from). On encountering end of file `fscanf` returns a special value `EOF` (which is macro constant defined in the standard library). Again, we must close the file at the end with `fclose`. We will now write to a binary file: @@ -1491,7 +1493,7 @@ int main(void) } ``` -Okay, don't get scared, this example looks complex because it trying to do a cool thing: it creates an image file! When run, it should produce a file named *image.ppm* which is a tiny 5x5 smiley face image in [ppm](ppm.md) format. You should be able to open the image in any good viewer (I wouldn't bet on [Windows](windows.md) programs though). The image data was made manually and are stored in the `image` array. We don't need to understand the data, we just know we have some data we want to write to a file. Notice how we can manually initialize the array with values using `{` and `}` brackets. We open the file for writing and in binary mode, i.e. with a mode `"wb"`, we check the success of the action and then write the whole array into the file with one function call. The function is name `fwrite` and is used for writing to binary files (as opposed to `fprintf` for text files). `fwrite` takes these parameters: pointer to the data to be written to the file, size of one data element (in bytes), number of data elements and a pointer to the file to write to. Our data is the `image` array and since "arrays are basically pointers", we provide it as the first argument. Next argument is 1 (`unsigned char` always takes 1 byte), then length of our array (`sizeof` is a special operator that substitutes the size of a variable in bytes -- since each item in our array takes 1 byte, `sizeof(image)` provides the number of items in the array), and the file pointer. At the end we close the file. +Okay, don't get scared, this example looks complex because it is trying to do a cool thing: it creates an image file! When run, it should produce a file named *image.ppm* which is a tiny 5x5 smiley face image in [ppm](ppm.md) format. You should be able to open the image in any good viewer (I wouldn't bet on [Windows](windows.md) programs though). The image data was made manually and are stored in the `image` array. We don't need to understand the data, we just know we have some data we want to write to a file. Notice how we can manually initialize the array with values using `{` and `}` brackets. We open the file for writing and in binary mode, i.e. with a mode `"wb"`, we check the success of the action and then write the whole array into the file with one function call. The function is name `fwrite` and is used for writing to binary files (as opposed to `fprintf` for text files). `fwrite` takes these parameters: pointer to the data to be written to the file, size of one data element (in bytes), number of data elements and a pointer to the file to write to. Our data is the `image` array and since "arrays are basically pointers", we provide it as the first argument. Next argument is 1 (`unsigned char` always takes 1 byte), then length of our array (`sizeof` is a special operator that substitutes the size of a variable in bytes -- since each item in our array takes 1 byte, `sizeof(image)` provides the number of items in the array), and the file pointer. At the end we close the file. And finally we'll finish with reading this binary file back: @@ -1524,10 +1526,59 @@ The file mode is now `"rb"` (read binary). For reading from binary files we use ## More on Functions (Recursion, Function Pointers) +There's more to be known about functions. + +An important concept in programming is [recursion](recursion.md) -- the situation in which a function calls itself. Yes, it is possible, but some rules have to be followed. + +When a function calls itself, we have to ensure that we won't end up in infinite recursion (i.e. the function calls itself which subsequently calls itself and so on until infinity). This crashes our program. There always has to be a **terminating condition** in a recursive function, i.e. an `if` branch that will eventually stop the function from calling itself again. + +But what is this even good for? Recursion is actually very common in math and programming, many problems are recursive in nature. Many things are beautifully described with recursion (e.g. [fractals](fractal.md)). But remember: anything a recursion can achieve can also be achieved by iteration (loop) and vice versa. It's just that sometimes one is more elegant or more computationally efficient. + +Let's see this on a typical example of the mathematical function called [factorial](factorial.md). Factorial of *N* is defined as *N* x *(N - 1)* x *(N - 2)* x ... x 1. It can also be defined recursively as: factorial of *N* is 1 if *N* is 0, otherwise *N* x *N - 1*. Here is some code: + +``` +#include + +unsigned int factorialRecursive(unsigned int x) +{ + if (x == 0) // terminating condition + return 1; + else + return x * factorialRecursive(x - 1); +} + +unsigned int factorialIterative(unsigned int x) +{ + unsigned int result = 1; + + while (x > 1) + { + result *= x; + x--; + } + + return result; +} + +int main(void) +{ + printf("%d %d\n",factorialRecursive(5),factorialIterative(5)); + return 0; +} +``` + +`factorialIterative` computes the factorial by iteration. `factorialRecursive` uses recursion -- it calls itself. The important thing is the recursion is guaranteed to end because every time the function calls itself, it passes a decremented argument so at one point the function will receive 0 in which case the terminating condition (`if (x == 0)`) will be triggered which will avoid the further recursive call. + +It should be mentioned that performance-wise recursion is almost always worse than iteration (function calls have certain overhead), so in practice it is used sparingly. But in some cases it is very well justified (e.g. when it makes code much simpler while creating unnoticeable performance loss). + +Another thing to mention is that we can have **pointers to functions**; this is an advanced topic so we'll stay at it just briefly. Function pointers are pretty powerful, they allow us to create so called *[callbacks](callback.md)*: imagine we are using some [GUI](gui.md) framework and we want to tell it what should happen when a user clicks on a specific button -- this is usually done by giving the framework a pointer to our custom function that it will be called by the framework whenever the button is clicked. + ## Dynamic Allocation (Malloc) ## Debugging, Optimization ## Advanced Stuff +## Final Program + ## Under The Hood \ No newline at end of file diff --git a/fsf.md b/fsf.md new file mode 100644 index 0000000..e722cef --- /dev/null +++ b/fsf.md @@ -0,0 +1,3 @@ +# FSF + +FSF stands for Free Software Foundation, a non-profit organization established by [Richard Stallman](rms.md) with the goal of promoting and supporting [free as in freedom software](free_software.md), software that respects its users' freedom. \ No newline at end of file diff --git a/gnu.md b/gnu.md new file mode 100644 index 0000000..ba8bd9d --- /dev/null +++ b/gnu.md @@ -0,0 +1,10 @@ +# GNU + +GNU (*GNU is Not Unix", a [recursive](recursion.md) acronym) is a project started by [Richard Stallman](rms.md), the inventor of [free as in freedom software](free_software.md), running since 1983 with the goal of creating a completely free (as in freedom) [operating system](os.md), along with other free [software](software.md) that computer users might need. The project achieved its goal of creating an operating system when a [kernel](kernel.md) named [Linux](linux.md) became part of it in the 90s as the last piece of the puzzle -- the system is now known as GNU/Linux. However, the GNU project didn't end and continues to further develop the operating system as well as a myriad of other software projects it hosts. GNU gave rise to the [Free Software Foundation](fsf.md) and is one of the most important software projects in history of computing. + +## See Also + +- [Free Software Foundation](fsf.md) +- [Richard Stallman](rms.md) +- [copyleft](copyleft.md) +- [free software](free_software.md) \ No newline at end of file diff --git a/main.md b/main.md index 33613fb..51f3006 100644 --- a/main.md +++ b/main.md @@ -6,6 +6,8 @@ This wiki is **NOT** a satire. **Before contributing please read the [rules & style](wiki_style.md)!** {But contributions aren't really accepted RN :) ~drummyfish } +We have a **[C tutorial](c_tutorial.md)**! + Pay us a visit on the [Island](island.md)! And come mourn with us in the [cathedral](cathedral.md), because **technology is dying**. If you're new here, you may want to read answers to [frequently asked questions](faq.md), including "Are you a fascist?" and "Do you love Hitler?". diff --git a/rms.md b/rms.md index 9365e17..8d077a1 100644 --- a/rms.md +++ b/rms.md @@ -2,12 +2,14 @@ The great doctor Richard Matthew Stallman (RMS, born 1953 in New York) is one of the biggest figures in software history, inventor of [free software](free_software.md), founder of the [GNU project](gnu.md), [free software foundation](fsf.md) and the author of a famous text editor [emacs](emacs.md). -Stallman's life along with free software's history is documented by a free-licensed book named *Free as in Freedom: Richard Stallman's Crusade for Free Software* on which he collaborated. You can get it for free e.g. at Project Gutenberg. You should read this! +Stallman's life along with free software's history is documented by a free-licensed book named *Free as in Freedom: Richard Stallman's Crusade for Free Software* on which he collaborated. You can get it for free e.g. at [Project Gutenberg](https://www.gutenberg.org/ebooks/5768). You should read this! -Stallman has a beautifully minimalist website http://www.stallman.org where he actively comments on current news and issues. +Stallman has a beautifully minimalist website http://www.stallman.org where he actively comments on current news and issues. Regarding [software](software.md) he has for his whole life strongly and tirelessly promoted free software and [copyleft](copyleft.md) and has himself only used such software; he has always practiced what he preched and led the best example of how to live without [proprietary](proprietary.md) software. This is amazing. Nevertheless he isn't too concerned about [bloat](bloat.md) (judging by the GNU software and his own creation, [emacs](emacs.md)) and he also doesn't care that much about [free culture](free_culture.md) (some of his written works prohibit modification and his GNU project allows proprietary non-functional data). +RMS made the free software song (well, only the lyrics, the melody is taken from a Bulgarian folk song Sadi Moma). + He is a weird person, having been recorded on video eating dirt from his feet before giving a lecture. In the book *Free as in Freedom* he admits he might be autistic. Nevertheless he's pretty smart, has magna cum laude degree in physics from Harvard, 10+ honorary doctorates, fluently speaks English, Spanish and French and has many times proven his superior programming skills (even though he later stopped programming to fully work on promoting the FSF). In 2019 Stallman was cancelled by SJW fascists for merely commenting rationally on the topic of child sexuality following the Epstein scandal. He resigned from the position of president of the FSF but continues to support it. \ No newline at end of file