The PE format uses RVAs (Relative Virtual Address). It is the value you need to add to the base address to get the linear address. The base address is the address the PE image is loaded to, and may vary from one invocation to the next.
For example, suppose an executable file is loaded to address 0x400000 and execution starts at RVA 0x1560. The effective execution start will then be at the address 0x401560. If the executable were loaded to 0x100000, the execution start would be 0x101560.
It becomes more complicated when the parts of the PE file (the sections) are not necessarily aligned the same way the loaded image is. For example, the sections of the file are often aligned to 512-byte-borders, but the loaded image may be aligned to 4096-byte-borders. So, to find a piece of information such as the IAT table in a PE-file for a specific RVA, you must calculate the offsets as if the file were loaded, but skip according to the file offsets.
When a compiler finds a call to a function that is in a DLL, it will, in the very simplist sense, not know anything about the DLL function and simply output a normal call-instruction to that symbol, the address of which the linker will have to fix, like it does for any type of external symbol. The linker uses an import library to look up from which DLL which symbol is imported, and produces stubs for all the imported symbols, each of which consists of a jump instruction; the stubs are the actual call targets. These jump instructions will actually jump to an address that is acquired from the import address table. In more advanced applications (when "__declspec(dllimport)" is used), the compiler knows the function is imported, and outputs a call to the address that's in the import address table, bypassing the jump.
Here is a link to a simple example for reading the IAT.