1. 程式人生 > >關於VS中LNK1120與errorLNK2019問題

關於VS中LNK1120與errorLNK2019問題

      最近遇到了該問題,再查找了一些資料後,發現了針對自己問題的解決方法,貼出來讓大家一起學習一下。

其實如果這兩個問題同時出現,很可能不是連結庫缺了lib,而是編譯中新增的源沒有被例項化,造成編譯時,機器以為是缺失lib。本人用的編譯器為vs2012,問題出在與,在.h聲明瞭函式後,在.hpp下進行了定義。問題在於.hpp不是其原始檔。所以最後生成LNK錯誤。以前自己移動過,再次新增原始檔沒注意,造成了.hpp沒有被認為是原始檔而是標頭檔案。

   下面是我看到的一個例子,分享一下。

摘自[1].http://q.cnblogs.com/q/34032/

  我在一個頭檔案裡定義了聲明瞭一個模版函式,如下:

//Combination.h
#ifndef VECTOR_H
#define VECTOR_H

#include <vector>

#endif

template<class T> void Combination(T a[], int len, int index, int m, std::vector<T>& c);
CPP裡定義
//Combination.cpp
#include "Combination.h"

using namespace std; 

template<class T> void Combination(T a[], int len, int index, int m, vector<T>& c)
{
    if(0 == m)
    {
        vector<T>::iterator iter = c.begin();
        for(; iter != c.end(); ++iter)
        {
            cout<<*iter;
        }
        printf("\n");
        return;
    }

    if(len == index)
        return;

    c.push_back(a[index]);
    Combination(a, len, index + 1, m - 1, c);
    c.pop_back();

    Combination(a, len, index + 1, m, c); 
}

main中呼叫
#include <iostream>
#include "Combination.h"

#ifndef VECTOR_H
#define VECTOR_H

#include <vector>

#endif

using namespace std;

void main()
{
    int a[] = {1,2,3,4,5,6};
    
    vector<int> c;
    Combination(a, sizeof(a) / sizeof(int), 0, 3, c);
        
    system("pause");
    return;
}

編譯連線時提示以下錯誤

錯誤 1 error LNK2019: 無法解析的外部符號 "void __cdecl Combination<int>(int * const,int,int,int,class std::vector<int,class std::allocator<int> > &)" ([email protected]@@[email protected][email protected]@[email protected]@@[email protected]@@Z),該符號在函式 _main 中被引用 main.obj CppTest
錯誤 2 fatal error LNK1120: 1 個無法解析的外部命令 D:\Documents\Visual Studio 2008\Projects\CppTest\Debug\CppTest.exe CppTest

解決方法:

把方法或類定義放到宣告的.h檔案中去。

      理解這個問題,需要一點編譯原理的知識,在呼叫一個方法或者使用一個類的時候,本cpp作為一個獨立的編譯單元,可能並不知道某一個方法或者型別的符號是怎麼樣的,但是這時候不會出錯,還是可以針對每個編譯單元生成目標檔案obj,之後針對沒有找到的方法或者型別符號,連結器會在別的obj檔案中尋找缺失的符號。

   假設模版函式可以放在標頭檔案中宣告,CPP中定義,按照你的例子分析一下:
main中呼叫Combination(a, sizeof(a) / sizeof(int), 0, 3, c);,也就是型別Combination(int, int,int,int, vector<int>&);但是編譯器並不知道Combination(int, int,int,int, vector<int>&);,因為這個型別並不在任何一個.h檔案中,之後編譯器會寄希望於連結器可以解決這個問題,也就是在Combination.cpp的編譯目標檔案Combination.obj中,但是Combination.obj也沒有這個型別,它有的只是一個模板定義。
C++標準裡規定: 當一個模板不被用到的時侯它就不該被例項化出來,Combination.cpp沒有用到Combination(int, int,int,int, vector<int>&);,所以也就不會編譯出來該符號,連結出錯也就可以理解了。



相關推薦

關於VSLNK1120errorLNK2019問題

      最近遇到了該問題,再查找了一些資料後,發現了針對自己問題的解決方法,貼出來讓大家一起學習一下。 其實如果這兩個問題同時出現,很可能不是連結庫缺了lib,而是編譯中新增的源沒有被例項化,造成編譯時,機器以為是缺失lib。本人用的編譯器為vs2012,問題出在與,在

解決VSDebugRelease版本切換的問題

最近在使用PCL以及VTK等開發庫,但是使用過程中總會出現Debug與Release版本之間切換的問題,完全按照網上各種大牛的教程來配置的開發環境,為啥會爆出各種錯誤呢,一開始我也是一頭霧水,明明在Debug或者Release模式下執行的好好地,可是切換模式後奇怪的錯誤

【MM ECC VS S4】MM模塊ECCS4的區別

ships sap request down rac erro load 能力 業務 原文出自 https://blogs.sap.com/2017/04/28/comparison-of-simplification-and-functionality-in-s4-and

完美解決--用VS的Git做代碼管理器,他人共享代碼

服務 git 新建 註冊郵箱 一起 下載 代碼管理 svn 進行 1、創建代碼倉庫,這裏說一下為什麽要創建倉庫,Git不能夠作為源代碼管理器,vs中自帶的也只能夠在本地進行管理,要和他們共享的話必須要有服務器端去存儲代碼,類似於SVN,它就有客戶端和服務器端,這裏推薦用Gi

vs的qt純qt不同的地方

qt雙擊右擊沒有轉到槽解決點擊拖動左邊是信號 右邊是槽 槽可以自己取名字按esc退出編輯槽記住名字這裏必須自己手動在頭這件裏再聲名下 (必需寫實現)有時要用this->控件時沒有用 要先編譯下ui文件添加類一般qt文件都在這裏面如果有插件時會找不到文件(如高亮插件)可以把文件放到同級目錄下 但會報錯

vs 項目 dll 一起調試和參數傳遞

dll1.打開 vs 創建項目2.添加項目3.配置 dll(exe的路徑)4.調試的時候倆個都最好生成一下 不然報錯 項目與 dll 之間的參數傳遞(結構體 函數指針等) 如DEBUG_EVENT 結構體 map<string, pVoidFun> (pVoidFun為函數指針)先導出一個函數實現

QTextEdit新增內容Qt在Vs中文顯示亂碼問題解決

vs中Qt中文顯示亂碼解決 最簡單的方法: #pragma execution_character_set("utf-8") QTextEdit  *m_textShower = new QTextEdit(); (1)設定字型的方法 QFo

VS找不到windowssdkdirVS的環境變數巨集

Visual Studio 2013(簡稱VS2013)編譯報錯: "warning MSB8003: Could not find WindowsSDKDir variable from the registry.  TargetFrameworkVersion or Platfor

Windows下openssl安裝vs的使用

由於專案需要在vs中呼叫openssl庫,因此簡單記錄一下最方便最簡單的方法 環境: OS:Windows 10  x64 VS: 2017 x86 0X00 在Windows中安裝openssl 。 在這個連結中可以找到這個地方,我下載了Win32 OpenSSL v

關於VS區分debugrelease,32位64位編譯的巨集定義

在vs程式設計中,常常涉及到32位和64位程式的編譯,怎麼判斷當前編譯是32位編譯還是64位編譯?如何判斷 是debug下編譯還是release下編譯?因為之前用到,這裡記錄一下,省的忘了又要瘋狂的google。 1.判斷是debug編譯還是release編譯。 如

關於vs出現lnk2019和lnk1120錯誤

今天配置vs2015+direcx時按照網上說的一步步的設定但是最後出現瞭如下錯誤lnk2019和lnk1120 然後上網搜尋了找到答案,別人說是一開始新建專案時錯了,應該新建win32application的,而我新建的是consoleapplication,但是在開頭

VSC++靜態/動態庫檔案的編譯除錯使用

基礎知識:不同語言之間可以通過呼叫動態連結庫 (dll)來呼叫別人寫好的函式同一語言可以呼叫別人寫好的靜態(lib)庫靜態連結庫:是通過靜態聯編的,在連結時,link將自己的(.obj)二進位制檔案和別人的lib檔案一起共同生成.exe檔案。 靜態連結庫的缺點是: 1)比較

vsSQL Server建立連線時出現網路相關的或特定的例項的錯誤。未找到或無法訪問伺服器

一般遇到這種情況(app_data中新增不了資料庫,伺服器管理中也連線不了)    幾種解決方案試一下: 1.開啟SQL server 配置管理器,開啟SQL Server網路配置-->SQLEXPRESS協議,檢查Named Pipes 和TCP/IP 是否已啟

R vs. Python,資料分析爭鋒?

R和Python兩者誰更適合資料分析領域?在某些特定情況下誰會更有優勢?還是一個天生在各方面都比另一個更好? 當我們想要選擇一種程式語言進行資料分析時,相信大多數人都會想到R和Python——但是從這兩個非常強大、靈活的資料分析語言中二選一是非常困難的。我

vs靜態庫動態庫的呼叫

解決問題:vs中如何呼叫庫。 1.什麼是庫 庫是寫好的現有的,成熟的,可以複用的程式碼。現實中每個程式都要依賴很多基礎的底層庫。 本質上來說庫是一種可執行程式碼的二進位制形式,可以被作業系統載入記憶體執行。 庫有兩種:靜態庫(.a、.lib)和動態庫(.so、.dll

JsonCpp在vs使用

com png img 平臺 json 找到 https make files Jsoncpp是c++生成和解析Json數據的跨平臺開源庫。下面簡介如何在vs中使用。 1、官網下載。https://sourceforge.net/projects/jsoncpp/解壓文件得

轉:JavaStringbyte[]的轉換

輸出字符串 單個字符 linu 編輯 繁體 中國人 對象 本質 計算機基礎知識 String s = "fs123fdsa";//String變量 byte b[] = s.getBytes();//String轉換為byte[] String t = new Stri

win10系統VMwareHyper-v不兼容

vmware hyper-v 因為知道win10中有一個自帶的虛擬機Hyper-v於是今天就去添加去試一試,體驗了一把。結果在需要使用VMware的時候遇上這個問題這個就很尷尬了,由於平時很多的測試都在VMware上操作,這個使得很多重要數據都在上面,這樣只能重新把Hyper-v給關了再重啟了,

java後臺讀取配置文件keyvalue -----demo

undle ltm string 文件名 logs 配置 rip conf 返回值 public class ResourcesUtils { /* * @description:根據屬性獲取文件名 * * @param:propertyName文件的

iOS開發地圖定位

視圖 編寫 aps 簡單 -a 第三方 span spa margin   不管是QQ還是微信的移動client都少不了定位功能,之前在微信demo中沒有加入定位功能,今天就寫個定位的小demo來了解一下定位和地圖的東西。地圖和定位看上去是挺高大上一東西。其有使用方法比