ahmed.o.mohamed

اختبر قدراتك في C/CPP - الحلقة الرابعة, الجزء الثالث

7 ردود في هذا الموضوع

السلام عليكم

الحلقة الأولى.

الحلقة الثانية - الجزء الأول.

الحلقة الثانية - الجزء الثاني.

الحلقة الثانية - الجزء الثالث.

الحلقة الثانية - الجزء الرابع.

الحلقة الثانية - الجزء الخامس.

الحلقة الثانية - الجزء السادس و الأخير.

الحلقة الثالثة - الجزء الأول.

الحلقة الثالثة - الجزء الثاني.

الحلقة الثالثة - الجزء الثالث.

الحلقة الثالثة - الجزء الرابع.

الحلقة الثالثة - الجزء الخامس و الأخير.

الحلقة الرابعة - الجزء الأول.

الحلقة الرابعة - الجزء الثاني.

مرحبا بكم إخوتي الكرام في الجزء الثالث من الحلقة الرابعة من سلسلة اختبر قدراتك, قمتُ بتقسيم الحلقة الرابعة إلى عدة أجزاء, مُرتبة حسب الصعوبة.

أجزاء هذه الحلقة ستكون خاصة بمسائل الــ OOP.

الإختبار الرابع (الجزء الثالث) :

قم بإنشاء فئة باسم stack_int تسمح بإجراء بعض العمليات على stack من الأعداد الصحيحة, هذه الأخيرة يتم حجزهم ديناميكياً و يتم إرسال الحجم إلى دالة البناء (نفترض أن القيمة الإفتراضية هي 20).

الفئة stack_int يجب أن تدعم العمليات التالية : (نفترض أن p كائن من الفئة stack_int و n عدد صحيح)

  • المؤثر << حيث تدل العملية p<<n على إضافة العدد n إلى المكدس p (إذا كان المكدس مملتئ, لا يحدث شيء)
  • المؤثر >> حيث تدل العملية p>>n على إسناد القيمة العليا في الــ Stack إلى المتغير n و حذف القيمة الأولى. (إذا كان المكدس فارغ, لا يتغير شيء)
  • المؤثر ++ حيث تكون نتيجة العملية ++p تُساوي 1, إذا كان المكدس ممتلئ أو 0 إذا كان العكس.
  • المؤثر -- حيث تكون نتيجة العملية --p تُساوي 1, إذا كان المكدس فارغ أو 0 إذا كان العكس.

نفترض أنه يُمكن استخدام المؤثرين << و >> هكذا :

p << n1 << n2 << n3 ;
Or
p >> n1 >> n2 << n3 ;

أيضا, يجب تصميم الفئة بحيث يستطيع المستخدم تحويل كائن من الصنف stack_int إلى مصفوفة عددية بينما لا يمكن إسناد كائن إلى آخر (يجب إظهار تنبيه و توقيف البرنامج عند محاولة إجراء عملية الإسناد).

كتابة الفئة يجب أن تتم بطريقتين مختلفتين :

  1. عن طريق إعادة تعريف المعاملات.
  2. باستخدام الــ template.

سأضع حل السؤال بعد إنتهاء عرض المحاولات.

2

شارك هذا الرد


رابط المشاركة
شارك الرد من خلال المواقع ادناه

سأبدأ أنا أولا هذه المرة :)

الطريقة الأولى :

stack_int.h

#include <cstdlib>
#include <iostream>
using namespace std;

class stack_int {
int nmax;
int nelem;
int * adv;
public:

stack_int(int n = 20) {
nmax = n;
adv = new int [nmax];
nelem = 0;
}

~stack_int() {
delete adv;
}

stack_int(stack_int & p) {
nmax = p.nmax;
nelem = p.nelem;
adv = new int [nmax];
int i;
for (i = 0; i < nelem; i++)
adv[i] = p.adv[i];
}

void operator =(stack_int & p) {
cout << "*** Tentative d'affectation entre piles - "
"arret execution ***" << endl;
exit(1);
}

stack_int & operator <<(int n) {
if (nelem < nmax) adv[nelem++] = n;
return (*this);
}

stack_int & operator >>(int & n) {
if (nelem > 0) n = adv[--nelem];
return (*this);
}

int operator ++() {
return (nelem == nmax);
}

int operator --() {
return (nelem == 0);
}

};

Main.cpp

#include "stack_int.h"

int main() {
void fct(stack_int);
stack_int pile(40);

cout << "Pleine : " << ++pile << " vide : " << --pile << endl;
pile << 1 << 2 << 3 << 4;
fct(pile);
int n, p;

pile >> n >> p;
cout << "Haut de la pile au retour de fct : " << n << " " << p << endl;
stack_int pileb(25);
pileb = pile;

return 0;
}

void fct(stack_int pl) {
cout << "Haut de la pile reçue par fct : ";
int n, p;
pl >> n >> p;
cout << n << " " << p << endl;
pl << 12;
}

المُخرجات:

post-219439-049310700 1347315718_thumb.p

الطريقة الثانية انتهيتُ أيضا من كتابتها, لكن سأضعها لاحقا حتى لا أحرق السؤال :happy:

2

شارك هذا الرد


رابط المشاركة
شارك الرد من خلال المواقع ادناه

أرى أن مستوى المشاركة قد انخفض !, أين أصحاب C++ ؟ :blink:

عموما, إليكم الطريقة الثانية :

stackg.h

#include <cstdlib>
#include <iostream>
using namespace std;

template <class T> class stack_gene {
public:
int nmax;
int nelem;
T * adv;
stack_gene(int = 20);
~stack_gene();
stack_gene & operator <<(T);
stack_gene & operator >>(T &);
int operator ++();
int operator --();
template <class U> friend ostream & operator <<(ostream &o, const stack_gene<U> &s);
};

template <class T> stack_gene<T>::stack_gene(int n) {
nmax = n;
adv = new T [nmax];
nelem = 0;
}

template <class T> stack_gene<T>::~stack_gene() {
delete adv;
}

template <class T> stack_gene<T> & stack_gene<T>::operator <<(T n) {
if (nelem < nmax) adv[nelem++] = n;
return (*this);
}

template <class T> stack_gene<T> & stack_gene<T>::operator >>(T & n) {
if (nelem > 0) n = adv[--nelem];
return (*this);
}

template <class T> int stack_gene<T>::operator ++() {
return (nelem == nmax);
}

template <class T> int stack_gene<T>::operator --() {
return (nelem == 0);
}

template <class T> ostream & operator <<(ostream & sortie, stack_gene<T> & p) {
sortie << "// ";
int i;
for (i = 0; i < p.nelem; i++) sortie << p.adv[i] << " ";
sortie << "//";
return sortie;
}

Main.cpp

#include "stackg.h"

int main() {
stack_gene <int> pi(20);
cout << "pi pleine : " << ++pi << " vide : " << --pi << endl;
pi << 2 << 3 << 12;
cout << "pi = " << pi << endl;

stack_gene <float> pf(10);
pf << 3.5 << 4.25 << 2;
cout << "pf = " << pf << endl;

float x;
pf >> x;
cout << "haut de la pile pf = " << x;
cout << "pf = " << pf << endl;

return 0;
}

المُخرجات :

post-219439-071184200 1347363823_thumb.p

0

شارك هذا الرد


رابط المشاركة
شارك الرد من خلال المواقع ادناه

جيد أنها ليست مصفوفة doublesmile.gif

هذا حلي للسؤال الأول ...

#include<cstdio>
class stack_int
{
private:
int *stack;
int size;
bool empty;
bool full;
int pointer;
public:
stack_int(unsigned _size=20)
{
size=_size;
if(size){
stack=new int [size];
empty=1;
full=0;
pointer=0;}
}
stack_int operator<<(int n)
{
if(!full)
{
empty=0;
stack[pointer]=n;
pointer++;
if(pointer==size)
full=1;
}
return *this;
}
stack_int operator>>(int n)
{
if(!empty)
{
stack[pointer]=n;
}
return *this;
}
bool operator++()
{
if(full)
return 1;
else
return 0;
}
bool operator--()
{
if(empty)
return 1;
else
return 0;
}
int*getArray()
{
int *array=new int[pointer];
for(int i=0;i<pointer;i++)
array[i]=stack[i];
return array;
}
void operator=(stack_int)
{
printf( "Error Can't support this operator\n" );
}
void show()
{
for(int i=0;i<pointer;i++)
{
printf("element[%i]=%i\n",i,stack[i]);
}
}
int getPointer()
{
return pointer;
}
};

void main()
{
stack_int a(5);
printf("is stack empty ? %i\n",--a);
a<<4;
a<<3;
printf("is stack empty ? %i\n",--a);
a<<1;
printf("is stack full ? %i\n",++a);
a<<12;
a<<32;
printf("is stack full ? %i\n",++a);
stack_int b;
a=b;
a.show();
int *array=a.getArray();
int size=a.getPointer();
for(int i=0;i<size;i++)
{
printf("array element[%i]=%i\n",i,array[i]);
}
}

ملاحظة : استعنت بحل الأخ أحمد عند تحميل عملية ++ لأنني لم أعرف ماذا أضع الوسيط ... فقد وضعته كائن من نوع stack_int فظهر خطاً !!

0

شارك هذا الرد


رابط المشاركة
شارك الرد من خلال المواقع ادناه

وهذه محاولتي مع template

stack_int.h

#include<cstdio>
template<class type> class stack_int
{
private:
type *stack;
type size;
bool empty;
bool full;
int pointer;
public:
stack_int(int _size=20)
{
size=_size;
if(size){
stack=new type [size];
empty=1;
full=0;
pointer=0;}
}
stack_int operator<<(type n)
{
if(!full)
{
empty=0;
stack[pointer]=n;
pointer++;
if(pointer==size)
full=1;
}
return *this;
}
stack_int operator>>(type n)
{
if(!empty)
{
stack[pointer]=n;
}
return *this;
}
bool operator++()
{
if(full)
return 1;
else
return 0;
}
bool operator--()
{
if(empty)
return 1;
else
return 0;
}
type*getArray()
{
type *array=new type[pointer];
for(int i=0;i<pointer;i++)
array[i]=stack[i];
return array;
}
void operator=(stack_int)
{
printf( "Error Can't support this operator\n" );
}
void show()
{
for(int i=0;i<pointer;i++)
{
printf("element[%i]=%i\n",i,stack[i]);
}
}
int getPointer()
{
return pointer;
}
};

main.cpp

#include"stack_int.h"
#define TYPE int
void main()
{
stack_int<TYPE> a(4);
printf("is stack empty ? %i\n",--a);
a<<4;
a<<3;
printf("is stack empty ? %i\n",--a);
a<<1;
printf("is stack full ? %i\n",++a);
a<<12;
a<<32;
printf("is stack full ? %i\n",++a);
stack_int<TYPE> b;
a=b;
a.show();
TYPE *array=a.getArray();
int size=a.getPointer();
for(int i=0;i<size;i++)
{
printf("array element[%i]=%i\n",i,array[i]);
}
}

وكانت مخرجات الكود كالتالي :

is stack empty ?  1
is stack empty ? 0
is stack full ? 0
is stack full ? 1
Error Can't support this operator
element[0]=4
element[1]=3
element[2]=1
element[3]=12
array element[0]=4
array element[1]=3
array element[2]=1
array element[3]=12

للأسف عندما غيرت النوع إلى double وحتى floatظهر warning بخصوص دالة البناء :

 warning C4244: 'initializing' : conversion from 'double' to 'int', possible loss of data
C:\Users\ThePrince\C++\Test.cpp(11) : while compiling class-template member function '__thiscall stack_int<double>::stack_int<double>(int)'

وطبعاً كانت النواتج محبطة حيث لم يتم تخزين أي عنصر!!!:

is stack empty ?  1
is stack empty ? 0
is stack full ? 0
is stack full ? 1
Error Can't support this operator
element[0]=0
element[1]=0
element[2]=0
element[3]=0
array element[0]=0
array element[1]=0
array element[2]=0
array element[3]=0

أكره الأعداد العشرية dry.gif

0

شارك هذا الرد


رابط المشاركة
شارك الرد من خلال المواقع ادناه

مصطفى

المشكلة ليست في float او double

غير %i إلى %f في printf

for(int i=0;i<size;i++)
{
printf("array element[%i]=%f\n",i,array[i]);
}

أما التحذير, فبخصوص كاست نوع العنصر size في الكلاس الى int لما تكون type != int, هذا نوعه int مهما كان, لا داعي لاعطائه نوع القالب

stack=new type[size]; // <==> stack=new type[(int)size]; --> (float or double) to int, possibl data loss

تم تعديل بواسطه khatibe_30
0

شارك هذا الرد


رابط المشاركة
شارك الرد من خلال المواقع ادناه

تم منح النقاط للمشاركات المفيدة و حذف الردود الغير مفيدة, حفاظا على تنسيق الموضوع.

يُغلق.

أراكم في الجزء الرابع من الحلقة الرابعة.

0

شارك هذا الرد


رابط المشاركة
شارك الرد من خلال المواقع ادناه
زوار
This topic is now closed to further replies.

  • يستعرض القسم حالياً   0 members

    لا يوجد أعضاء مسجلين يشاهدون هذه الصفحة .