خطأ تسجيل C ++ قبل المعالج وحدات الماكرو __LINE__، __FUNCTION__

StackOverflow https://stackoverflow.com/questions/622129

  •  05-07-2019
  •  | 
  •  

سؤال

وأنا في محاولة لدمج خطأ بسيط تسجيل في بلدي التطبيق الحالي، في هذه اللحظة تقارير الأخطاء فقط باستخدام cout حيث كان يأمل أن يحافظ على واجهة مماثلة باستخدام مشغل <<. ولكن أريد أن تسجيل الخط وتعمل وقوع الخطأ، ولكن أنا لا أريد أن يكون للكتابة __LINE__, __FUNCTION__ في كل مرة أحتاج إلى تسجيل. لا أحد يعرف خدعة يمكنني استخدامها للسماح الماكرو __LINE__ لاستخدامها داخل وظيفة أخرى، الإبلاغ عن خط الدعوة بدلا من ذلك؟ نأمل أن من المنطقي.

class myLogClass {
    uint8_t level;                  
public:                 
    bool operator<<( const char * input );          
};

bool myLogClass::operator<<( const char * input ) {
    logItInSQL( input );
    return true;
}

وبدلا من هذا في كل مرة

myLogClass << "Line No: " << __LINE__
    << " Function: " << __FUNCTION__
    << " Error: " << "This is my error to be logged";

وأود أن يكون مجرد قادرا على القيام به:

myLogClass << "This is my error to be logged";

bool myLogClass::operator<<( const char * input ) {
    logItInSQL( " Line No: __LINE__" );
    logItInSQL( " Function: __FUNCTION__" );
    logItInSQL( " Error: " + input );
    return true;
}
هل كانت مفيدة؟

المحلول

myLogClass << "Line No: " << __LINE__ ...

ومع تسلسل operator << الخاص بك لن تعمل منذ تقوم بإرجاع bool.

bool myLogClass::operator << (const char * input)

ومن المعتاد أن تحدد تيار الإدراج كما يلي:

std::ostream& myLogClass::operator << (std::ostream& o, const char * input) {
    // do something
    return o;
}

هل هذا:

#define log(o, s) o << "Line No: " << __LINE__ << \
                   " Function: " << __FUNCTION__ << \
                   " Error: " << s // note I leave ; out

وبالإضافة إلى ذلك، يمكنك لف الماكرو في حلقة do-while:

#define log(o, s) do { o << "Line No: " << __LINE__ << \
                   " Function: " << __FUNCTION__ << \
                   " Error: " << s; \ 
                  } while(0) // here, I leave ; out

وبعد ذلك يمكنك كتابة بسعادة:

 myLogClass myLogger; // do this

 // use it
log(myLogger, "This is my error to be logged"); // note the ;

نصائح أخرى

في ANSI C (التي يجب أن تعمل أيضا في C ++ أفترض)، يمكنك القيام بذلك باستخدام وظائف variadic وحدات الماكرو المعالج. انظر المثال أدناه:

#include <stdio.h>
#include <stdarg.h>

#define MAXMSIZE 256
#define MyDebug(...) MyInternalDebug(__FILE__,__FUNCTION__,__LINE__,__VA_ARGS__)

void MyInternalDebug( char *file, char *function, const int line, const char *format, ... )
{
    char message[MAXMSIZE];
    // Variable argument list (VA)
    va_list ap;
    // Initialize VA
    // args : Name of the last named parameter in the function definition.
    // The arguments extracted by subsequent calls to va_arg are those after 'args'.
    va_start(ap, format);

    // Composes a string with the same text that would be printed if 'format' was used on printf,
    // but using the elements in the variable argument list identified by 'ap' instead of
    // additional function arguments and storing the resulting content as a C string in the buffer pointed by 'message'.
    // * The state of arg is likely to be altered by the call.
    vsprintf(message, format, ap);
    // Custom print function
    printf("%s\t%s\t%d\t%s\n",file, function, line, message);

    // Finzalize use of VA
    va_end(ap);
}

int main ()
{  
    MyInternalDebug(__FILE__, __FUNCTION__, __LINE__, "An error occured with message = '%s'", "Stack Overflow");
    MyDebug("Another error occured with code = %d", 666);

    return 0;
}

لا، وهذا هو السبب يتم تسجيل مع وحدات الماكرو. __LINE__ يحتاج إلى توسيع من قبل المعالج على الخط في السؤال، وليس في وظيفة تسجيل المشتركة.

وكما ذكر آدم Mitz تحتاج إلى استخدام __LINE__ في مكان المكالمة.
أوصي لكم لإضافة معلمة إضافية مثل "additionalInfo" وإنشاء ماكرو من شأنها أن تولد هذه "additionalInfo" باستخدام __LINE__ و__FUNCTION __.

وأنا لم أستطع الحصول على التعليمات البرمجية في الجواب الأول لتجميع. يمكنني استخدام هذا الماكرو البسيط الذي يحقق هذه المهمة أيضا:

و#define qlog(s) std::cerr << __FUNCTION__ << "::" << __LINE__ << "\t" << s << endl

مرخصة بموجب: CC-BY-SA مع الإسناد
لا تنتمي إلى StackOverflow
scroll top