c ++从数组中删除一个最大值和零

时间:2017-08-28 16:20:40

标签: c++ arrays

我有一个内部有10个值的双数组,首先我的函数应该从数组中找到并删除最大值,如果该值在数组中只有一次,其次从数组中删除零值。在这一点上,我们不能使用任何向量来解决这个问题。

<script src="https://ajax.googleapis.com/ajax/libs/jquery/3.2.1/jquery.min.js"></script>
<script src="https://ajax.googleapis.com/ajax/libs/jqueryui/1.12.1/jquery-ui.min.js"></script>
<link href="https://ajax.googleapis.com/ajax/libs/jqueryui/1.12.1/themes/smoothness/jquery-ui.css" rel="stylesheet"/>
<div style="position: absolute;">
<ul id="menu">
  <li class="ui-state-disabled"><div>Toys (n/a)</div></li>
  <li><div>Books</div></li>
  <li><div>Clothing</div></li>
  <li><div>Electronics</div>
    <ul>
      <li class="ui-state-disabled"><div>Home Entertainment</div></li>
      <li><div>Car Hifi</div></li>
      <li><div>Utilities</div></li>
    </ul>
  </li>
  <li><div>Movies</div></li>
  <li><div>Music</div>
    <ul>
      <li><div>Rock</div>
        <ul>
          <li><div>Alternative</div></li>
          <li><div>Classic</div></li>
        </ul>
      </li>
      <li><div>Jazz</div>
        <ul>
          <li><div>Freejazz</div></li>
          <li><div>Big Band</div></li>
          <li><div>Modern</div></li>
        </ul>
      </li>
      <li><div>Pop</div></li>
    </ul>
  </li>
  <li class="ui-state-disabled"><div>Specials (n/a)</div></li>
</ul>
</div>
<div>
Text above button
</div>
<div>
  <button id="dropdownbtn">Show menu</button>
</div>
<div>
Text below button
</div>

4 个答案:

答案 0 :(得分:0)

为了从数组中删除元素,您需要将所有剩余元素“向上”移动一个,以便array[i] = array[i+1];

另一种方法是指示阵列插槽可以重用。

请参阅std::vector::erasestd::array

答案 1 :(得分:0)

这看起来很像编程课程作业?无论如何,我会采取两通方式:

第一遍有两个任务:

  1. 找出最重要的元素并记住它;还要确保它只有一次。
  2. 计算零的数量。
  3. 在代码中:

    if (n == 0)
        return; //just to be safe
    
    size_t max_value = first[0];
    bool max_value_is_unique = true;
    size_t zeroes = first[0] == 0 ? 1 : 0;
    //start at 1, since we already looked at first[0] above!
    for (size_t i = 1; i < n; ++i) {
        //oh, it's a 0; count it!
        if (first[i] == 0)
            zeroes++;
    
        //check if this is equal to or bigger than current maximum
        if (first[i] == max_value)
            max_value_is_unique = false;
        else if (first[i] > max_value) {
            max_value = first[i];
            max_value_is_unique = true;
        }
    }
    

    优化: 如果没有唯一的最大元素且零的数量为0,则返回:

    if (zeroes == 0 && !max_value_is_unique)
        return;
    

    否则,运行第二遍:

    这个只会将条目从右侧移动到您当前的位置。 一旦我们达到0或最大值,移动距离就会增加,因为我们想要跳过该值。

    //move all entries some distance "to the left"
    int distance = 0;
    for (size_t i = 0; i < n - distance; /* no increment! */) {
        bool might_inc = true;
        //we skip the current value in case it's a zero or the maximum value
        if ((max_value_is_unique && first[i] == max_value) || first[i] == 0)
            distance++;
    
        if (distance > 0) {
            if (i + distance < n) {
                //we might reach out of the array here, so this line guarded
                first[i] = first[i + distance];
                //since we just copied some value to the current `i`, we need to take a look at that `i` it again - it might be 0 or the maximum value
                might_inc = false;
            } else
                //if we would reach out of the array, write 0
                first[i] = 0;
         }
    
         if (might_inc)
             i++;
    }
    
    //you didn't specify it, so I'll just set the remaining entries to 0
    for (int i = n - distance; i < n; ++i) {
        first[i] = 0;
    }
    

    我没有像所有零一样检查角落情况,但我认为它应该有用。 如果你知道有X尾随零,而不是复制&amp;然后检查复制的值,您可以在复制前检查该值。但是,正如我所说,它看起来像一个练习,长度是10,那么好,应该没问题; - )

    如果您不知道size_t,那么这是一个奇特的数据类型,它总是足以满足您的整个内存。 在此代码中,您很可能只需编写unsigned intint。但认为size_t是更好的风格,在适当的时候严格使用它是一种很好的做法。

答案 2 :(得分:0)

您的代码完全错误

你的第一个for循环应该只用来找到最大值和计数,每次你找到一个更大的值,你需要重置你的计数器,k

然后使用另一个for循环去除值,i + 1可以超出边界而n--会阻止你遍历整个数组

用于删除值的for循环也是错误的,你应该有两个数字来表示保持和探测的索引。

例如,要从[1,0,0,4]中删除0,您的代码将以[1,0,4,4]结尾并将大小更改为2

答案 3 :(得分:0)

你的删除是在搜索中 - 错误的

你实际上并不需要计算最大值

您无法通过简单float比较doublelong double==等浮点值。您需要测量它们之间的差异,如果它小于一些小的容差值,则认为它们相等。

所以......试试这个:

#include <iostream>
#include <cstddef>
#include <cmath>
#include <cstdlib>

void remove_all(double* array, std::size_t& size, double val) {
    double eps = 1e-9; 
    std::size_t k = 0, tail = 0;
    while (k + tail < size) {
        if (std::fabs(array[k + tail] - val) < eps) // correct floating point numbers equality compare
            ++tail;
        else {
            array[k] = array[k + tail];
            ++k;
        }
    }
    size -= tail;
}

void remove_max_and_zeros(double* array, std::size_t& size) {
    //-- find max element in array --
    double maxVal = array[0];
    for (std::size_t k = 0; k < size; ++k) 
        if (maxVal < array[k])
            maxVal = array[k];
    //-- remove max element from array --
    remove_all(array, size, maxVal);
    //-- remove zeros from array --
    remove_all(array, size, 0.0);
}

int main()
{
    const std::size_t maxSize = 10;
    double arr[maxSize] = { 1.1, 1.3, 0.0, 2.5, 0.0, -5.8, 2.5, 0.0, 0.0001, 0.0 };
    std::size_t size = maxSize;

    for (std::size_t k = 0; k < size; ++k)
        std::cout << arr[k] << " ";
    std::cout << std::endl;

    remove_max_and_zeros(arr, size);

    for (std::size_t k = 0; k < size; ++k)
        std::cout << arr[k] << " ";
    std::cout << std::endl;
    return 0;
}