الفريق العربي للبرمجةأرشيف المنتديات · 2000 – 2023
نسخة أرشيفية للقراءة فقط — التسجيل والمشاركة مغلقان، والمحتوى محفوظ كما كان.

كيف اكتب templateفي h , ccp

بدأه سار مع الليل في 2 مارس 2011 · 15 رد · 1,254 مشاهدة · في الأسئلة المجابة
مشاركة: واتساب X فيسبوك تيليجرام
#1 صاحب الموضوع

السلام عليكم ورحمة الله وبركاتة

بارك الله فيكم جميعاً

ماهو الخطاء في الكود التالي حيث انة عند استخدام template تظهر المشكلة وعندما امسح Template من الكود يشتغل تمام

ملف الـ header



#ifndef h_stacktype
#define h_stacktype

template <class Type>
class stacktype
{
Type *list;
int top;
int stacksize;
public:
stacktype( int size=10);
};
#endif



ملف ccp


#include "stdafx.h"
#include "stacktype.h"
template <class Type>
stacktype<Type>::stacktype(int size)
{
top=0;
stacksize=size;
list =new Type [stacksize];
}


ملف الدالة الرئيسية main


#include "stdafx.h"
#include "stacktype.h"
#include <iostream>
using namespace std;

int _tmain(int argc, _TCHAR* argv[])
{
stacktype<char> s(20);

return 0;
}

حيث ان الرسالة التي تظهر عند تنفيذ الكود هي


unresolved external symbol "public: __thiscall stacktype<char>::stacktype<char>(int)" (??0?$stacktype@D@@QAE@H@Z) referenced in function _wmain

1
49940.jpg
#2

اولاً اخي لا انصحك ان تستمر بأستخدام ال project بطريقه Microsoft للبرامج البسيطه انشيء ملفات ال cpp وال .h لوحدك

ثانياً:

الخطاء في اماكن وضع للكود على ما اعتقد لانه لا مشكله بالكود بحد ذاته.

ما هي اسماء الملفات التي نسخت فيها هذا الكود ؟؟

#3

ملف stacktype.h يحتوي على الكود الاول وهو كتالي

#ifndef h_stacktype
#define h_stacktype

template <class Type>
class stacktype
{
        Type *list;
        int top;
        int stacksize;
public:
        stacktype( int size=10);
};
#endif

ملفstacktype.cpp يحتوي على الكود التالي

#include "stdafx.h"
#include "stacktype.h"
template <class Type>
stacktype<Type>::stacktype(int size)
{
        top=0;
        stacksize=size;
        list =new Type [stacksize];
}

وملف الدالة الرئيسية

stackTemplate.cpp

انا استخدم برنامج vs 2008

وهنا صورة للتوضيح

templatead.jpg

تم تعديل هذه المشاركة بواسطة سار مع الليل في 2 مارس 2011 في 17:21

49940.jpg
#4

اضف السطر التالي في نهايه ال stacktype.cpp

template class stacktype<char>;

ليصبح :

#include "stdafx.h"
#include "stacktype.h"
template <class Type>
stacktype<Type>::stacktype(int size)
{
        top=0;
        stacksize=size;
        list =new Type [stacksize];
}

template class stacktype<char>;
#5

اضف في نهاية ملف الهيدر stacktype.h:

#include "stacktype.cpp"

حل مشكله Undefined Reference عند التعامل مع الTemplate

بالتوفيق،

1

http://informatic-ar.com منصة تعليمية عربية في علوم الحاسب والبرمجة

https://moalfat.com  للكتب الالكترونية والكورسات التعليمية

Everything we see now is just an engineering solution based on old science

#6

او انصحك ان تنقل التعريف لداخل ملف ال h. حتى ترتاح من هذه المشكله نهائياً

2
#7
Wajdy Essam كتب:

اضف في نهاية ملف الهيدر stacktype.h:

#include "stacktype.cpp"

حل مشكله Undefined Reference عند التعامل مع الTemplate

بالتوفيق،

شكراً اخي الغالي على تعاونك وبارك الله لك واحسن اليك

لقد استخدم طريقتك وهي كتالي

#ifndef h_stacktype
#define h_stacktype

template <class Type>
class stacktype
{
	Type *list;
	int top;
	int stacksize;
public:
	stacktype( int size=10);
};
#include "stacktype.cpp"
#endif

ولكن للاسف لم تنجح تظهر هذه الرسالة

'stacktype<Type>::stacktype(int)' : function template has already been defined

Ali Al-Zyoud كتب:

او انصحك ان تنقل التعريف لداخل ملف ال h. حتى ترتاح من هذه المشكله نهائياً

كيف انقل التعريف داخل ملف h

هل انقل جميع الدوال الى h

وماذا عن ملف cpp

=================================================================================

=================================================================================

Ali Al-Zyoud كتب:

اضف السطر التالي في نهايه ال stacktype.cpp

template class stacktype<char>;

ليصبح :

#include "stdafx.h"
#include "stacktype.h"
template <class Type>
stacktype<Type>::stacktype(int size)
{
        top=0;
        stacksize=size;
        list =new Type [stacksize];
}

template class stacktype<char>;

شكراً اخي الغالي وبارك الله لك واحسن اليك وزادك علماً

نعم طريقتك هي الصحيحة

ولكن ممكن اعرف لماذا هكذا فعلت

الطريقة نجحت تمام ولكن لم افهم شي

ممكن توضح ولو قليل

لاني برامج التالية كلها تعتمد على template

تم تعديل هذه المشاركة بواسطة سار مع الليل في 2 مارس 2011 في 20:41

49940.jpg
#8

لو استخدمت خمسة كائنات من انواع بيانات مختلفة على سبيل المثال الكود التالي

#include "stdafx.h"
#include "stacktype.h"
#include <iostream>
using namespace std;

int _tmain(int argc, _TCHAR* argv[])
{
	stacktype<int> s(20);
	stacktype<float> f;
	stacktype<char> c;
	stacktype<string> w;
	stacktype<double> e;
	stacktype<long> a;


	return 0;
}

هل يجب ان اكتب داخل ملف cpp

template class stacktype<int>;
template class stacktype<float>;
template class stacktype<char>; 
template class stacktype<string>; 
template class stacktype<double>; 
template class stacktype<long>;
49940.jpg
#9

الى الاخ العزيز Ali Al-Zyoud

لا اعرف كيف اشكرك

الله يشهد

ان جميع مشاركاتي وانت ترد علي وتجاوبني وجميع مشاركاتك تكون حلول صحيحة ومقنعة ولي اكثر من سنة وانت تجاوب علي من الاساسيات الى اليوم

انت ساعتني من الاساسيات وهي التكرار والمصفوفات والموشرات وانت نصحتني ان ادرس oop قبل data struction ولقد عملت بنصيحتك (والله انها فادتي افادة كثيرة)

الحمدلله الان انا في data struction واستخدم معها oop

فوالله لولا نصيحتك لما عرفت كيف استخدم oop مع data struction

لان جميع الكتب حق مادة data strcution شرحها وامثلتها باستخدام oop

فانا الان استخدم معها الوراثة وتعدد الاشكال وغيرها

بقي علي tempalte وهو سهل فهمة

ولكن عندما اطبقة مع data struction تظهر المشاكل التي ارفقتها لكم وانت بارك الله لك تساعدني

لذلك شكراً لك وجزاك الله خير واغفر لك ماتقدم وماتاخر من نذبك

والله لا اعرف كيف اشكرك ولكن مابيدي الا الدعاء لك واكثر الله من امثالك

وشكراً للمنتدى الغالي ولاعضائة

49940.jpg
#10

كيف تضيف التعاريف لملف ال .h ؟

بشكل التالي

اولاً قم بحذف ملف ال cpp الخاص بال class

ثانياً سيصبح ملف ال header بشكل التالي:

#ifndef h_stacktype
#define h_stacktype

template <class Type>
class stacktype
{
	Type *list;
	int top;
	int stacksize;
public:
	stacktype<Type>::stacktype(int size)
	{
		top=0;
		stacksize=size;
		list =new Type [stacksize];
	}
};
#endif
#11

اقراء الموضوع التاي لتعرف بشكل واضح ما هي المشكله:

http://www.codeguru.com/forum/showthread.php?t=250284

طبعاً هذه المشكله تضهر فقط عند استخدام ال Templates .

المشكله هي في تفسير ال compiler للكود.

من الحلول الجيده بأضافه كبمه export في بدايه تعريف ال method ولكن المشكله معضم الكومبايلرز لا تدعم ذلك

#12

ظهرت مشكلة لأنك واضع

#include "stakctype.h"

في ملف الcpp.

فقم بحذف هذا السطر (ولا تنسى اضافة ملف الcpp في اخر ملف الهيدر)،، وسوف يعمل ان شاء الله..

بالتوفيق،،

http://informatic-ar.com منصة تعليمية عربية في علوم الحاسب والبرمجة

https://moalfat.com  للكتب الالكترونية والكورسات التعليمية

Everything we see now is just an engineering solution based on old science

#13

الـ templates لا يمكن وضع الكود الخاص بها داخل translation unit و ذلك لأن الكود الفعلي الذى يتم ترجمته يتم توليده بناءا على الكود الخاص بالـ template لذا لابد أن يكون كود الـ template داخل ملف الـ header.

أحد الأساليب المتبعه لكتابة كود الـ template داخل ملف منفصل هى بصنع ملف بإمتداد "inl" و هو إختصارا لـ inline و بداخله تقوم بكتابة الكود بشكل مباشر و بعدها تقوم بعمل include لذلك الملف فى اخر ملف الـ header.

احد الأخطاء الشائعه عند استخدام ملف inl هو انك تقوم بعمل include لملف الـ header الذى تكتب الكود لأجله و هذا فعل خاطئ لأن كود ملف inl سيتم تضمينه لاحقا داخل ملف الـ header.

لذا فى حالتك هذه سيوجد لديك ملفين فى نفس المجلد احدهما اسمه stacktype.h و الأخر أسمه stacktype.inl و محتوياتهما كالتالي:

// stacktype.h

#ifndef h_stacktype
#define h_stacktype

template <class Type>
class stacktype
{
        Type *list;
        int top;
        int stacksize;
public:
        stacktype( int size=10);
};

#include "stacktype.inl"


#endif

// stacktype.inl

template <class Type>
stacktype<Type>::stacktype(int size)
{
        top=0;
        stacksize=size;
        list =new Type [stacksize];
}

و الله ولي التوفيق

تم تعديل هذه المشاركة بواسطة محمد علاء الدين في 4 مارس 2011 في 15:05

1

مدونتي: C++ Tips and Tricks

#14
محمد علاء الدين كتب:

الـ templates لا يمكن وضع الكود الخاص بها داخل translation unit و ذلك لأن الكود الفعلي الذى يتم ترجمته يتم توليده بناءا على الكود الخاص بالـ template لذا لابد أن يكون كود الـ template داخل ملف الـ header.

أحد الأساليب المتبعه لكتابة كود الـ template داخل ملف منفصل هى بصنع ملف بإمتداد "inl" و هو إختصارا لـ inline و بداخله تقوم بكتابة الكود بشكل مباشر و بعدها تقوم بعمل include لذلك الملف فى اخر ملف الـ header.

احد الأخطاء الشائعه عند استخدام ملف inl هو انك تقوم بعمل include لملف الـ header الذى تكتب الكود لأجله و هذا فعل خاطئ لأن كود ملف inl سيتم تضمينه لاحقا داخل ملف الـ header.

لذا فى حالتك هذه سيوجد لديك ملفين فى نفس المجلد احدهما اسمه stacktype.h و الأخر أسمه stacktype.inl و محتوياتهما كالتالي:

// stacktype.h

#ifndef h_stacktype
#define h_stacktype

template <class Type>
class stacktype
{
        Type *list;
        int top;
        int stacksize;
public:
        stacktype( int size=10);
};

#include "stacktype.inl"


#endif

// stacktype.inl

template <class Type>
stacktype<Type>::stacktype(int size)
{
        top=0;
        stacksize=size;
        list =new Type [stacksize];
}

و الله ولي التوفيق

اخي الغالي

كيف انشاء ملف inl بدل ملف cpp

لم اجد طريقة لانشاء ملف inl

49940.jpg
#15

داخل الـ solution explorer قم بتغيير إمتداد الملف من cpp إلى inl.

و الله ولي التوفيق

مدونتي: C++ Tips and Tricks

#16
محمد علاء الدين كتب:

داخل الـ solution explorer قم بتغيير إمتداد الملف من cpp إلى inl.

و الله ولي التوفيق

شكراً اخي الغالي

لقد جربت الطريقة وفعلاً نجحت

شكراً لك

49940.jpg

مواضيع مشابهة