Gcc कमांड लाइन में, मैं एक स्ट्रिंग को परिभाषित करना चाहता हूं, जैसे -Dname=Mary
कि सोर्स कोड में मैं printf("%s", name);
प्रिंट करना चाहता हूं Mary
।
मैं यह कैसे कर सकता था?
Gcc कमांड लाइन में, मैं एक स्ट्रिंग को परिभाषित करना चाहता हूं, जैसे -Dname=Mary
कि सोर्स कोड में मैं printf("%s", name);
प्रिंट करना चाहता हूं Mary
।
मैं यह कैसे कर सकता था?
जवाबों:
दो विकल्प। सबसे पहले, उद्धरण चिह्नों से बचें ताकि शेल उन्हें न खाए:
gcc -Dname=\"Mary\"
या, यदि आप वास्तव में चाहते हैं -डैम = मैरी, तो आप इसे कड़े कर सकते हैं, हालांकि यह थोड़ा हैकी है।
#include <stdio.h>
#define STRINGIZE(x) #x
#define STRINGIZE_VALUE_OF(x) STRINGIZE(x)
int main(int argc, char *argv[])
{
printf("%s", STRINGIZE_VALUE_OF(name));
}
ध्यान दें कि STRINGIZE_VALUE_OF खुशी से एक मैक्रो की अंतिम परिभाषा तक का मूल्यांकन करेगा।
अब तक मैंने पाया सबसे पोर्टेबल तरीका \"Mary\"
- यह न केवल gcc के साथ बल्कि किसी अन्य C कंपाइलर के साथ काम करेगा। उदाहरण के लिए, यदि आप /Dname='"Mary"'
Microsoft संकलक के साथ उपयोग करने का प्रयास करते हैं , तो यह एक त्रुटि के साथ बंद हो जाएगा, लेकिन /Dname=\"Mary\"
काम करेगा।
उबंटू में मैं एक उपनाम का उपयोग कर रहा था जो सीएफएलएजीएस को परिभाषित करता है, और सीएफएलएजीएस में एक मैक्रो शामिल है जो एक स्ट्रिंग को परिभाषित करता है, और फिर मैं सीएफएलएजीएस को मेकफाइल में उपयोग करता हूं। मुझे दोहरे उद्धरण वर्ण और साथ ही \ वर्ण से बचना था। यह कुछ इस तरह देखा गया:
CFLAGS='" -DMYPATH=\\\"/home/root\\\" "'
1) DEFINES=-DLOGPATH=\"./logfile\" CFLAGS = -v $(DEFINES)....
2) DEFINES=-DLOGPATH=\\\"./logfile\\\" CFLAGS = "-v $(DEFINES)...."
-v संकलक विकल्प का उपयोग यह देखने के लिए उपयोगी है कि प्रीप्रोसेसर क्या कर रहा है।
ये रहा एक सरल उदाहरण:
#include <stdio.h>
#define A B+20
#define B 10
int main()
{
#ifdef __DEBUG__
printf("__DEBUG__ DEFINED\n");
printf("%d\n",A);
#else
printf("__DEBUG__ not defined\n");
printf("%d\n",B);
#endif
return 0;
}
अगर मैं संकलन करता हूं:
$gcc test.c
आउटपुट:
__DEBUG__ not defined
10
अगर मैं संकलन करता हूं:
$gcc -D __DEBUG__ test.c
आउटपुट:
__DEBUG__ defined
30
यह मेरा समाधान है: -DUSB_PRODUCT=\""Arduino Leonardo\""
मैंने इसे
मेकफाइल में इस्तेमाल किया: GNU मेक 3.81 (GnuWin32 से)
और
avr-g ++ (AVR_8_bit_GNU_Toolchain_3.5.0_1662: 4.9.2
एक precompiled फ़ाइल में परिणाम (जी ++ के लिए विकल्प) है:
const u8 STRING_PRODUCT[] __attribute__((__progmem__)) = "Arduino Leonardo";
FYI करें: जाहिरा तौर पर एक ही टूलचैन के विभिन्न संस्करण एक ही सिस्टम पर इस संबंध में अलग तरह से कार्य कर सकते हैं ... (जैसा कि, ऐसा लगता है कि यह एक शेल-पासिंग मुद्दा होगा, लेकिन स्पष्ट रूप से यह केवल शेल तक सीमित नहीं है)।
यहाँ हमारे पास xc32-gcc 4.8.3 बनाम (avr-) gcc 4.7.2 (और कई अन्य) समान मेकफाइल और main.c का उपयोग करके, एकमात्र अंतर है 'make CC=xc32-gcc'
, आदि।
CFLAGS += -D'THING="$(THINGDIR)/thing.h"'
कई पर उपयोग में रहा हैकई वर्षों में gcc (और बैश) के संस्करणों ।
इसे xc32-gcc के साथ संगत बनाने के लिए (और यह दावा करते हुए कि "" की तुलना में अधिक पोर्टेबल है) के बाद, निम्न कार्य करना होगा:
CFLAGS += -DTHING=\"$(THINGDIR)/thing.h\"
ifeq "$(CC)" "xc32-gcc"
CFLAGS := $(subst \",\\\",$(CFLAGS))
endif
वास्तव में इसे खोजने में भ्रमित करने वाली चीजें : जाहिरा तौर पर एक unquoted- डी के साथ // परिणाम में एक #define के अंत में एक टिप्पणी के साथ ... उदा।
THINGDIR=/thingDir/
-> #define /thingDir//thing.h
->#define /thingDir
(उत्तर एस यहाँ से मदद के लिए धन्यवाद , btw)।
मैंने अभी पाया कि हमारा एक एप्लिकेशन उबंटू पर संकलित नहीं है। चूंकि लिनक्स और विंडोज एक सामान्य दृष्टिकोण पर सहमत नहीं थे, इसलिए मैंने इसका इस्तेमाल किया:
NAME := "Mary"
ifeq ($(SystemRoot),)
# building on another OS
CFLAGS_ADD += -Dname=\"Mary\"
else
# building on Windows
CFLAGS_ADD += -Dname=\\\"Mary\\\"
endif
{
"version": "2.0.0",
"tasks": [
{
"type": "cppbuild",
"label": "C/C++: g++.exe build active file",
"command": "C:\\Program Files\\mingw-w64\\x86_64-8.1.0-posix-seh-rt_v6-rev0\\mingw64\\bin\\g++.exe",
"args": [
"-g",
"-DSHERAJ",
"${file}",
"-o",
"${fileDirname}\\${fileBasenameNoExtension}.exe"
],
"options": {
"cwd": "C:\\Program Files\\mingw-w64\\x86_64-8.1.0-posix-seh-rt_v6-rev0\\mingw64\\bin"
},
"problemMatcher": [
"$gcc"
],
"group": {
"kind": "build",
"isDefault": true
},
"detail": "compiler: \"C:\\Program Files\\mingw-w64\\x86_64-8.1.0-posix-seh-rt_v6-rev0\\mingw64\\bin\\g++.exe\""
}
]
}
मैंने #define SHERAJ
यहां वीएस कोड में किया है। यह प्रतिस्पर्धात्मक प्रोग्रामिंग के लिए बहुत अच्छा है -
int main() {
ios_base::sync_with_stdio(0);
cin.tie(0);
cout.tie(0);
#ifdef SHERAJ
freopen("input.txt" , "r", stdin);
#endif
int T;
cin>>T;
for(int test_case = 1;test_case<=T;test_case++) {
cout<<"Hello World"<<endl;
}
}
इसने मेरे लिए मैक और विंडोज दोनों पर वीएस कोड के लिए काम किया। अन्य तरीके यहाँ वर्णित हैं "-Dname=\"SHERAJ\""
और "-Dname=\\\"SHERAJ\\\""
मेरे लिए काम नहीं करते हैं।
तो इसका जवाब है "-DSHERAJ"
-DNAME=\"Mary\"
टोकन के लिए ऑल-कैप्स ( ) का उपयोग करें जो आप इस तरह से परिभाषित करने जा रहे हैं, ताकि वे अन्य मैक्रो की तरह दिखें।