最近我在一次工作面试中被问到这个问题。我诚实地说,我知道符号链接的行为和如何创建一个,但不了解硬链接的使用,以及它与符号链接的区别。


当前回答

当原始文件被移动时,硬链接非常有用。例如,将文件从/bin移动到/usr/bin或/usr/local/bin。到/bin中文件的任何符号链接都将被破坏,但是硬链接(直接到文件的inode的链接)不会关心。

硬链接可能占用更少的磁盘空间,因为它们只占用一个目录条目,而符号链接需要自己的inode来存储它所指向的名称。

Hard links also take less time to resolve - symlinks can point to other symlinks that are in symlinked directories. And some of these could be on NFS or other high-latency file systems, and so could result in network traffic to resolve. Hard links, being always on the same file system, are always resolved in a single look-up, and never involve network latency (if it's a hardlink on an NFS filesystem, the NFS server would do the resolution, and it would be invisible to the client system). Sometimes this is important. Not for me, but I can imagine high-performance systems where this might be important.

I also think things like mmap(2) and even open(2) use the same functionality as hardlinks to keep a file's inode active so that even if the file gets unlink(2)ed, the inode remains to allow the process continued access, and only once the process closes it does the file really go away. This allows for much safer temporary files (if you can get the open and unlink to happen atomically, which there may be a POSIX API for that I'm not remembering, then you really have a safe temporary file) where you can read/write your data without anyone being able to access it. Well, that was true before /proc gave everyone the ability to look at your file descriptors, but that's another story.

说到这里,恢复一个在进程a中打开,但在文件系统中未链接的文件需要使用硬链接来重新创建inode链接,这样当打开该文件的进程关闭或离开时,该文件不会消失。

其他回答

加上以上所有答案,查找硬链接和软链接文件的差异可以理解为:

在当前目录中有一个文件f6,还有一个名为t2的目录。

名为f1和。/t2/f2的文件是到f6的符号链接。

f7和。/t2/f8文件是f6的硬链接。

要找到软链接和硬链接,我们可以使用:

$ find -L . -samefile f6 

> ./f1
> ./f6
> ./f7
> ./t2/f2
> ./t2/f8

找到硬链接,我们可以使用:

$ find . -xdev -samefile f6

> ./f6
> ./f7
> ./t2/f8

因为硬链接可以在同一个文件系统上创建,所以我们可以在同一个文件系统/挂载点中搜索所有没有使用-L选项的硬链接(使用-xdev选项)。它节省了不必要的搜索到不同的挂载点。

所以搜索硬链接比搜索软链接快一些(如果我错了或不清楚,请纠正)。

符号链接链接到路径名。它可以在系统文件树中的任何位置,甚至在创建链接时不需要存在。目标路径可以是相对路径,也可以是绝对路径。

硬链接是指向inode的附加指针,这意味着它们只能存在于与目标相同的卷上。到文件的附加硬链接与用于引用文件的“原始”名称难以区分。

一个目录条目链接一个结构:

struct dentry{
    ino_t ino;
    char  name[256];
}

ino是inode的编号,name是文件名,inode结构可能是这样的:

struct inode{
      link_t nlink; 
      ...
}

例如,你创建一个文件/1,目录条目可能是这样的:

struct dentry{
     ino_t ino; /* such as 15 */
     char  name[256]; /* "1" */
} 

inode结构可能是这样的:

   struct inode{ /* inode number 15 */
         link_t nlink; /* nlink = 1 */
         ...
    }

然后你创建一个硬链接(可能是/100),目录条目可能是这样的:

  struct dentry{
     ino_t ino; /* 15 */
     char  name[256]; /* 100 */
  }

inode结构可能是这样的:

   struct inode{ /* inode numebr 15 */
         link_t nlink; /* nlink = 2 */
         ...
    }

然后你创建一个符号链接(可能是/200)到文件1,目录条目可能是这样的:

  struct dentry{
        ino_t ino; /* such as 16 */
        char  name[256]; /* "200" */
  }

inode结构可能是这样的:

   struct inode{ /* inode number 15 */ 
         link_t nlink; /* nlink = 2 */
         ...
    }

   struct inode{ /* inode number 16 */
         link_t nlink; /* nlink = 1 */
         ...
    } /* the data of inode 16 maybe /1 or 1 */

我刚刚发现了一个简单的方法来理解硬链接在一个常见的场景,软件安装。

有一天,我下载了一个软件到下载文件夹进行安装。在我做sudo make install后,一些可执行文件被cped到本地bin文件夹。这里,cp创建硬链接。我对这个软件很满意,但很快就意识到,从长远来看,下载并不是一个好地方。所以我把软件文件夹移动到源目录。好吧,我仍然可以像以前一样运行软件而不用担心任何目标链接的事情,就像在Windows中一样。这意味着硬链接可以直接找到inode和其他文件。

从MSDN,

符号链接

A symbolic link is a file-system object that points to another file system object. The object being pointed to is called the target. Symbolic links are transparent to users; the links appear as normal files or directories, and can be acted upon by the user or application in exactly the same manner. Symbolic links are designed to aid in migration and application compatibility with UNIX operating systems. Microsoft has implemented its symbolic links to function just like UNIX links. Symbolic links can either be absolute or relative links. Absolute links are links that specify each portion of the path name; relative links are determined relative to where relative–link specifiers are in a specified path

绝对符号链接的一个例子

X: "C:\alpha\beta\absLink\gamma\file"
Link: "absLink" maps to "\\machineB\share"
Modified Path: "\\machineB\share\gamma\file"

一个相对符号链接的例子

X: C:\alpha\beta\link\gamma\file
Link: "link" maps to "..\..\theta"
Modified Path: "C:\alpha\beta\..\..\theta\gamma\file"
Final Path: "C:\theta\gamma\file"

硬链接

硬链接是文件的文件系统表示形式 多个路径引用同一个卷中的单个文件。

要在windows中创建硬链接,请导航到要创建链接的位置并输入以下命令:

mklink /H Link_name target_path

请注意,您可以以任何顺序删除硬链接,而不管它们是按什么顺序创建的。同时,硬链接不能创建时

引用位于不同的本地驱动器中 参考包括网络驱动器。换句话说,其中一个引用是一个网络驱动器 要创建的硬链接与目标在同一路径

NTFS支持另一种称为结的链接类型。MSDN对它的定义如下:

连接(也称为软链接)与硬链接的不同之处在于,它引用的存储对象是单独的目录,并且连接可以链接位于同一计算机上不同本地卷上的目录。否则,连接与硬链接的操作相同。

硬链接部分和结节部分的粗体部分显示了两者的基本区别。

命令在窗口中创建一个连接,导航到要创建链接的位置,然后输入:

mklink /J link_name target_path