所以,我有一個這樣的檔案結構:
- 檔案A
- 檔案B
- 檔案C
FileA 包括 FileB 和 FileC
檔案B有:
#define image(i, j, w) (image[ ((i)*(w)) (j) ])
和 FileC 有:
#define image(i, j, h) (image[ ((j)*(h)) (i) ])
在編譯時我得到:
warning: "image" redefined
note: this is the location of the previous definition ...
此警告是否意味著它更改了在編譯時最初找到它的另一個檔案的定義?
有什么方法可以在維護這兩個定義的同時避免此警告,并且它們將不同的定義應用于各自的檔案?
先感謝您 :)
uj5u.com熱心網友回復:
此警告是否意味著它更改了在編譯時最初找到它的另一個檔案的定義?
該程式格式不正確。該語言沒有指定在這種情況下會發生什么。如果編譯器接受格式錯誤的程式,那么您必須閱讀編譯器的檔案以了解它們在這種情況下會做什么。
請注意,該程式甚至可能無法與其他編譯器一起編譯。
有什么方法可以在維護這兩個定義的同時避免此警告,并且它們將不同的定義應用于各自的檔案?
從技術上講,您可以像這樣使用 hack 而不觸及任何標題:
#include "FileB"
#undef image
#include "FileC"
但是一個好的解決方案 - 如果您可以修改標題 - 是不使用宏。編輯標題以擺脫它們。改用函式,并在不同的命名空間中宣告它們,以免它們的名稱發生沖突。
一些經驗法則:
- 不要使用不必要的宏。函式和變數優于宏。
- 如果您絕對需要使用宏,請遵循僅對宏名稱使用大寫的通用約定。確保宏名稱不與非宏混合很重要,因為宏不尊重命名空間或作用域。
- 如果您需要在單個標頭中使用宏,則在不再需要時立即取消定義它,而不是將其泄漏到其他標頭中。
- 不要使用沒有命名空間的名稱。這將導致名稱沖突。宏不尊重 C 命名空間,但您可以在它們的名稱前加上前綴。例如,您可以擁有
FILE_B_IMAGE和FILE_C_IMAGE(或基于具體背景關系的更具描述性的內容)。
它們在功能上并不等效,一個可以看作是行式迭代,另一個是列式迭代
這似乎是重命名函式(或宏,如果由于某種原因無法替換它們)的一個很好的論據。沿著這些路線呼叫一個row_wise和另一個column_wise或其他東西。使用描述性名稱!
uj5u.com熱心網友回復:
此警告是否意味著它更改了在編譯時最初找到它的另一個檔案的定義?
對于 GCC(標記),這意味著從重新定義開始使用第二次處理的定義,不僅包括在同一個檔案中,還包括在翻譯單元中出現宏識別符號后跟(. 以前的出現將使用以前的定義。
C 語言規范和 C 語言規范都沒有提供更通用的答案:除具有相同標記序列之外的重定義違反語言約束,因此包含這種不匹配重定義的程式的翻譯行為和執行行為都是未定義的.
有什么方法可以在維護這兩個定義的同時避免此警告,并且它們將不同的定義應用于各自的檔案?
如果這些定義僅在其各自的檔案中使用,那么最簡單的解決方案是將每個檔案#undef image放在最后。這適用于 C 和 C 。
如果兩者都打算公開以供其他檔案使用,那么您將遇到名稱沖突,您必須以一種或另一種方式解決該沖突。例如,您可以在定義和每個定義的所有用途中添加一個可區分的前綴。僅在 C 中,您還可以選擇通過將宏更改為 [行內] 函式并將它們放在不同的命名空間中來解決名稱沖突。與為名稱添加前綴相比,這可能會使每個用戶更容易適應新名稱。
uj5u.com熱心網友回復:
正如@Jarod42 所說,行內函式將解決問題。
轉載請註明出處,本文鏈接:https://www.uj5u.com/qianduan/339974.html
