Just something I ran into and couldn't think of a proper explanation. If I create an empty *.txt file on my PC and then look at its size, it shows 0. But how is that possible? I mean even if the file itself is empty, it still must have some size, just to store its own name. How can this be explained? (Non OS specific)
It's possible because there really is no file. There's just a directory entry with a name and owner. The directory entry is logically distinct from the file. For example, the same file can have more than one name in more than one directory.
Unfortunately, the term "file" isn't always used to mean precisely the same thing. But the file size logic comes from the model where a directory entry "attaches" a file to a directory and file names and related metadata are stored in the directory.
The semantic meaning of "file size" is different from the one you are using.
There are many file sizes which are meaningful. The most common one, and the one you are seeing here, is "the number of bytes in the file." If the file is an empty text file, it may indeed contain 0 bytes. This number is important to programmers because we often need to open a file, "read all the data," and close it. We need to know how many bytes of data will be in the file so we can plan ahead.
Another meaning arises from the way most file systems store data. Most file systems store data in blocks. For example, the file system may store data in 64kB blocks, meaning it will never allocate anything which is not an even multiple of 64kB. This sounds inefficient, but it can make bookkeeping quite a lot simpler, and often simpler means faster.
A third meaning, which you are tugging at, would be the actual number of bits required on the harddrive to describe the presence of a file. This includes information that is usually stored separately from the file. For instance, in Linux, the concept of the "filename" is stored in the inode for the directory containing the file (edit: from comments, technically this is stored in the directory's data. When I wrote this, I was thinking of the small-directory case. Data smaller than 156 bytes can be stored directly in the inode). This is not a commonly used meaning, because it is terribly hard to determine without knowing tremendously deep inner workings of your file system (did you account for the space needed to store all the permissions on the file?). However, if you have a 1,000,000 byte hard drive, and want to know how big of a file fits on that hard drive, this will be a very important meaning to you!
The file name is stored somewhere else.
Your disk will have a "file system" on it, put simply a method for choosing how file names and files are represented and interpreted on the physical disk.
On most Windows disks you will be using a file system called "NTFS" (New Technology File System"), this stores filename information in the Master File Table (MFT) separate from the file contents. See the Wikipedia article on Master File Table.
The file itself will therefore be of length 0 bytes, but its entry in the MFT will still occupy some space.
This is quite an interesting ontological question...
The file itself is the content of the file. If the file has no content, it has a size of zero. The file name is as much a part of the file as your own name is physically a part of you (ie, it isn't).
Just as your name exists as an idea in people's heads (and your own) that refers/points to the physical you, the file name exists in the file system's directory tree and it refers/points to the file.
(A little late to the answer ...)
How can a file be size zero is a little more complicated than provided by the above answers. The question is tagged Win7, but looking at other "simpler" file systems such as FAT or NTFS, may be useful as the concepts are similar.
The disk does not "know" what is a file and what is a directory; it's all data in little blocks. The OS distinguishes between the meaning of data blocks. The first few a special, but the rest of the blocks hold either information about the data (eg: file name, file length, first data block holding the data), or the data itself.
A directory is a special "file" whose "data" the OS understands is an information block containing information about files, not the content of the files. A good analogy is a physical library and the card catalog. Think of the information blocks as the card catalog and the shelves as the data blocks (card catalog also sits on a shelf-like structure).
When you "create" a file (say with UNIX
touch command), the OS first creates an entry in an information block (directory), with the following:
- Name = My_File.txt
- Length = 0
- Starting Data Block = N/A
- Additional info (owner, permissions, created/updated/modified date), etc
Only if there is some data to "write" does it attempt to find an empty data block to store the data. But the data blocks come in fixed sizes (say 32K) convenient for the disk to get to and the OS to read. If you only write "Hello", most of the block is "empty" (actually may not be zeros, but garbage from what was there before), so the table also now updates the size to the length (say 5 chars + End of File) so you don't get the bad stuff.
When you update the "file" to a length > block size, the OS writes the data to the new block and updates a data block to say the file continues onto next block AFTER the first (and so on) and the length is updated the new length (details differ).
What you end up with is a collection of information data blocks (directories or lists) with information about the chains of data blocks (file contents).
Logically, this also explains why a file move on the same filesystem is blinking fast while a copy takes a long time. The OS only has to edit 2 directory blocks to remove the entry from one directory (information data block) and add to another. Delete a file: just remove the entry in the directory block, freeing up the file data blocks to be reallocated.
ps: Just because the card catalog has entry for a book does not mean it's on the shelve (checked out or lost perhaps); file size 0.
pps: A misplaced book inside library implies search library, or in computer terms: chkdsk or repair disk!
A greater understanding can be gleaned by reading about UNIX inodes or appreciating how version control systems (ClearCase, TFS, Git, etc.) manage not only files and directories, but also versions of files and even versions of directories. In most cases, everything is stored in a database and presented to the user to appear as classical directory structure and files!
We have some excellent answers here - I'd just to add the picture version (a thousand words and all that.)
This is what one of my NTFS-formatted hard drives look like if you visualize it with a disk defragmenting tool. The MFT (Master File Table) is shown in violet:
That little violet square describes the list of files present in my HD. In rough terms it is, for a NTFS disk, what the Table of Contents is for a book; instead of pages, it points to their physical location on the rest of the disk1.
A file with a zero-bytes size can be visualized as a Table of Contents entry that points to no page at all:
The entry is there, listed - but since no page is indicated, we can assume that the content is non-existent.
1 - Surely, it's a little bit more complicated than that; but points like sector maps, mirror MFTs, etc. are out of this questions' scope.
Filesystems store a lot of information about a file such as file name, file size, creation time, access time, modified time, created user, user and group permissions, fragments, pointer to clusters that store the file, hard/soft links, attributes... Those are called file metadata. Why do you count those metadata into file size when users do not (need to) care about them and don't know about them? They only really care about the file content
Moreover each filesystem stores different types of metadata which take different amounts of space on disk. For example POSIX permissions are very different from NTFS permission, and there are also
inode numbers in POSIX which do not exist on Windows. Even POSIX filesystems vary a lot, like ext3 with 32-bit block address, ext4 with 48-bit, Btrfs with 64-bit and ZFS with 128-bit address. So how will you count those metadata into file size?
Take another example with a 100-byte file whose metadata consumes 56 bytes on the current filesystem. We copy the file to another filesystem and now it takes 128 bytes of metadata. However the file contents are exactly the same, the number of bytes in the files are also the same. So displaying file size as 156 bytes on a system but 228 bytes on another is very confusing and counter-intuitive.
A file size of
0, is similar to saying: I have a paper with
5 words on it. And on another paper, it has
0 words on it. So
0 is entirely possible.
The file's meta data (creation date time, last modified date time, file owner, permissions), are all stored else where and not included as part of the file size.
Understand it in a simple manner... when you create a file .. there is a directory entry generated which works as a pointer for the memory location of the file identified by the file name you provide. The size of the directory increases as you create more and more pointers or say files.. while the file size will increase only if you put ssome data at the pointed place i.e. inside the file itself. Till then the size will be zero. :)
So this is how it works:
As soon as you create any file on a volume it creates an file record in the NTFS mata file i.e. $MFT (Master file table). Since there is a FRS (File record segment) present in the MFT you will see a record. Each file record is of size 1 KB by default in case of NTFS file system. But that space is only claimed if you store some information inside the file. Even though you just write a single letter "a" considering that it is a text file, it will claim 1 KB of space because that is the default size of the FRS. The letter "a" goes to the default and unnamed data stream of that FRS, $Data which is a attribute where all you data goes if you don't have a ADS (Alternate Data Stream).
Let me know if you come up with any questions.