a file descriptor
/ FD /
When you check a coat at a theatre, you do not get the coat itself, you get a little numbered ticket. Later you hand back the ticket and the cloakroom finds your coat. A file descriptor is exactly that ticket. When your program opens a file, the OS does not hand you the file or even its address; it hands you a small non-negative integer, and from then on every read, write, or close you do refers to the file by that number.
Concretely, a file descriptor is an index into your process's open-file table. When you call open and it succeeds, the OS finds the lowest free slot in your per-process table, fills it in so it points at the right open-file structure, and returns that slot number, say 3. Your call read(3, buf, 100) means "use the file my slot 3 refers to." By long-standing Unix convention every process starts with three descriptors already open: 0 is standard input (usually the keyboard), 1 is standard output (usually the screen), and 2 is standard error. That is why a program can print without opening anything: it just writes to descriptor 1.
Why it matters: the descriptor is a deliberately opaque, tiny token, which keeps programs simple and the OS in control. Because it is just an index into a per-process table, the same number 3 means totally different files in two different processes, and a program cannot use a number to reach a file it never opened. A frequent confusion is mixing up the descriptor with the file's name or with the position: the descriptor is neither; it is a per-process handle, and the position it leads to lives over in the shared open-file structure.
fd = open("data.bin") returns 3. Now read(3, buf, 64) reads 64 bytes; close(3) releases it. In a different running program, descriptor 3 might be a network socket entirely, the number only has meaning within one process.
A small integer that indexes your process's open-file table, the OS keeps the real state.
Descriptors 0, 1, 2 are conventionally standard input, output, and error. The descriptor is a per-process index, not the file's name and not the position; the same number means different files in different processes.