2015-11-25 2 views
0

Я работаю над этим личным проектом, и я немного смущен тем, как работает функция remove().правильное использование функции remove()?

Заголовок:

class IntSet { 

public: 

    IntSet(); //Constructor 
    ~IntSet(); //Destructor 
    int size() ; // 
    bool isEmpty(); 
    bool contains(int number1); 
    void add(int number2); 
    void remove(int number2); 

private: 
    int* ptr; //pointer to the array 
    int sizeOfArray; //current size of the array 
    int currentValue; //number of values currently in IntSet 
}; 

основной (включая только добавить() часть)

 #include "IntSet.hpp" 
    #include <iostream> 

    IntSet::IntSet(){ 

     sizeOfArray = 10; 
     currentValue = 0; 
     ptr = new int[10]; 

    } 



    IntSet::~IntSet(){ 
     delete[] ptr; 
    } 

    //returning the number of values in the IntSet 

    int IntSet::size() 
    { 
     return currentValue; 
    } 

    //Determining whether the stack is empty 

    bool IntSet::isEmpty() 
    { 
     if (currentValue == 0) 
      return true; 
     else 
      return false; 
    } 

    //defining contains() function 

    bool IntSet::contains(int number1) 
    { 
     for (int i = 0; i < currentValue; i++) 
     { 
      if (ptr[i] == number1) 
       return true; 
     } 

     return false; 
    } 

     //defining add() function 

     void IntSet::add(int number2) 
     { 
      if (currentValue == sizeOfArray) 
      { 
       sizeOfArray = sizeOfArray * 2; //doubling size of arrayCapacity 

       int* temp = new int[sizeOfArray]; //allocating new one that's twice as large 

       for (int i = 0; i < currentValue; i++) 
       { 
        temp[i] = ptr[i]; //copying old stuff into new one 
       } 

       delete[] ptr; //deallocate old array 
       ptr = temp; //set ptr to new array 
      } 

     } 

    //defining remove() function goes here 

Так для функции Add(), я должен был принять параметр ИНТ добавить его в массив. Когда он заполняется, мне нужно удвоить размер массива, скопировать содержимое старого массива в новый, перенаправить указатель на элемент данных в новый массив и затем освободить массив.

Для функции remove() мне нужно просто взять параметр int и удалить его из IntSet, переместив все последующие элементы массива. Должен ли я просто использовать части моей функции добавления и в значительной степени рассказывать об этом для моей функции remove()? Если нет, как мне даже начать писать функцию remove()? При необходимости я покажу остальную часть кода. Спасибо вам, ребята!

+0

Вы хотите, чтобы он удалял int в определенной позиции, первый int с тем же значением или каждый int с этим значением? –

+0

В месте, где нужно удалить i, переместите каждый элемент с i + 1 на i, соблюдая порядок конца массива. –

+0

Вы не добавляете 'number2' в массив в функцию' add'. Вы оставили это, потому что нам это не нужно? –

ответ

0

Дайте этому попытку удаления:

void IntSet::remove(int number2) 
{ 
    bool bIntRemoved = false; 
    for(int i=0; i < currentValue; i++){ 
     // check if we are currently searching or shifting 
     if(!bIntRemoved){ 
      // still searching 
      // check if we should remove int at current index 
      if(ptr[i] == number2){ 
       // found the int to remove 
       // We'll decrement i and set bIntRemoved = to true 
       // So the else-if code handles shifting over the array 
        i--; 
       bIntRemoved = true; 
      } 
     }else if(i < currentValue-1){ 
      // We have spots to shift 
      // Check if this is the last index 
      ptr[i] = ptr[i+1]; 
     } // else, we are at the last index and we have nothing to shift 
    } 

    if(bIntRemoved){ 
     // The int was successfully located and any necessary shifting has been 
     // executed. Just decrement currentValue so the current last index will be 
     // disregarded. 
     currentValue--; 
    } // else, the int to remove could not be located 
} 

Я не проверял, но в теории, это должно найти первый экземпляр ИНТ вам нужно удалить, переместить все значения влево на одну точку (если int для удаления находится в последнем индексе массива), а затем уменьшает переменную currentValue, поэтому предыдущий последний индекс массива игнорируется и может быть перезаписан. В любом случае, извините, если это плохое объяснение, но это не самая простая концепция, чтобы объяснить. Я попытался достаточно хорошо документировать код, так что, надеюсь, это будет иметь смысл: P Сообщите мне, если у вас есть какие-либо вопросы и дайте мне знать, если это работает или не работает для вас (Я считаю, что отзывы очень важны.)

EDIT: Кроме того, я намерен говорить об этом, но я забыл, так что спасибо, @Viet, за упоминание этого в ответе, ваша add() функция не кажется обрабатывать случаи, когда currentValue меньше размер массива. Я предполагаю, что вы уже справляетесь с этим, и вы просто опустили заявление else, которое позаботится об этом?

EDIT # 2: Ниже код, чтобы правильно обращаться с добавлением новых элементов в массиве:

void IntSet::add(int number2){ 
    if (currentValue == sizeOfArray) 
    { 
     sizeOfArray = sizeOfArray * 2; //doubling size of arrayCapacity 

     // nothrow is used below to allow for graceful error handling if there is not enough 
     // ram to create the new array 
     int* temp = new (nothrow) int[sizeOfArray]; //allocating new one that's twice as large 

     // check if new int array could be create 
     if(temp == nullptr){ 
      // new int array could not be created 
      /** Possibly set an error flag here or in some way warn the calling function that 
       the function failed to allocate the necessary memory space. 
       I'll leave that up to you, OP. **/ 

      // Right now we'll just return without modifying the existing array at all 
      return; 
     } 

     for (int i = 0; i < currentValue; i++) 
     { 
      temp[i] = ptr[i]; //copying old stuff into new one 
     } 
     delete[] ptr; //deallocate old array 
     ptr = temp; //set ptr to new array 

     // Now we'll just let the code below add the number to the array 

    } // else we have enough space to add the number to the array 

    ptr[currentValue] = number2; 
    currentValue++; 
} 

Опять же, я не проверял этот код, но дайте мне знать, если он работает или делает не работает для вас. Кроме того, я изменил строку, которая делает новый массив (int *temp = new int[sizeOfArray];) обрабатывать ошибки, если память не может быть успешно распределена. Для этого я использую объект (nothrow) (подробнее об этом на this CPlusPlus page). Если распределение не выполняется, значение temp установлено на нулевой указатель. Без этого метод вместо этого отправит исключение bad_alloc или программа завершится. Это не очень грациозно, поэтому я предпочитаю правильно обрабатывать ошибку (и обрабатывать ее таким образом, что она менее напряженная для вызывающей функции). Чтобы использовать это, вам нужно будет включить заголовок <new> (где определено nothrow).

+0

oh и btw это имеет смысл! У меня есть вопрос. если бы я использовал функцию removeDifferent() и removeSame() для удаления одинаковых/разных чисел из say, установите A и установите B, я бы просто использовал код remove() там? – inkling123

+0

@ inkling123, если я правильно понимаю ваш вопрос об 'removeSame()' и 'removeDifferent()', то да, теоретически у вас может быть какая-то функция дедупликации, которая бы удаляла числа одинаковые или разные. Если бы я писал это, я бы объединил вашу функцию 'contains()' с этой функцией 'remove()'. Просто назовите что-то вроде 'if (setB.contains (value))' (тот же) или 'if (! SetB.contains (value))' (разные) для каждого значения в массиве setA. Для этого вам, вероятно, нужно будет изменить 'ptr' для публики, или вам нужно будет добавить метод getter для значений по заданным индексам в' ptr'. – SpencerD

+0

ah spencer, по какой-то причине ваша функция remove() работала плавно, но ваш add() не сделал, я понятия не имею, почему!но все же работали. (входит в комплект) – inkling123

0

Является ли ваш класс набором или списком?Если ваш класс является набором, это означает, что в вашем классе нет одинаковых номеров Пример: набор {1, 2, 3}, список: {1, 2, 3, 1, 3, 2}

О вашей функции добавления, у меня есть некоторые комментарии:

  • Вы не проверяет новый элемент существует в вашем наборе
  • Вы не увеличивает размер текущего и заданного значения для нового элемента в наборе
  • Вы можете использовать memcpy для копирования старых данных в новый указатель данных

О функции УДАЛИТЬ, у меня есть некоторые идеи:

  • Во-первых, вы должны найти позицию номер, который нужно будет удалить в текущем наборе
  • После этого, вы удалите это число сдвиг влево всех члена из следующей позиции числа, которое необходимо удалить в левую позицию. И вы должны уменьшить текущий размер 1

Пример: у вас есть множество {1, 2, 3, 4}, текущий размер 4. И вы хотите, чтобы удалить номер "2"

  • Сначала вы найдете позицию 2 в своем наборе. Это 1 (потому что начальный индекс массива начинается с 0)
  • Во-вторых, вы удаляете его, отбрасывая все значения из следующей позиции в передней части своего набора. Ex: значение позиции 1 заменено на значение 3, значение позиции 2 заменено на значение 4
  • Наконец, вы уменьшаете текущий размер на 1. Теперь текущий размер равен 3, и у вас есть новый набор {1, 3, 4}
+0

Мой класс - это набор, извините, что не оставлял это. Большое вам спасибо за вашу помощь – inkling123

Смежные вопросы