【问题标题】:finding out the divisors of a number找出一个数的除数
【发布时间】:2013-10-06 10:42:44
【问题描述】:

找出一个数的除数的最优化方法是什么,使得除数中至少有数字3?

例如21=1,3,7,21

因此只有一个除数包含数字 3。

例如 62=1,2,31,62

因此只有一个除数中有数字 3,即 31

编辑-我意识到最好的方法是找出一个数字的所有因数并检查包含数字 3 的因数。

找出因素的最佳方法:

Getting Factors of a Number

What is the best way to get all the divisors of a number?

【问题讨论】:

  • @Bunyip 我不必在这里计算除数的数量。查看约束(除数中应包含数字 3)。
  • @Bunyip,说相关帖子,即找到除数,然后过滤它们以找到其中包含 3 的除数。
  • @khajvah 那么这些除数的数量将是 3
  • 输入范围是多少?如果它足够小,请构建一个包含所有“有效”数字的表格,并检查您的数字是否可以除以每个数字。该表将变为 [3, 13, 23, 31, 32, 34, ...] (可以立即省略早期数字的倍数)。

标签: c++ optimization sieve-of-eratosthenes number-theory


【解决方案1】:

这是我的扩展。它首先检查列表div3 中是否存在可能 因素。如果没有,它会将候选者添加到 number/2,跳过已经可以根据此列表考虑的值,因此添加了 '37' 和 '43',但不添加 '36' 或 '39 '。

以上部分应视为“设置”。如果你知道输入约束(一个最大输入值),你可以计算一次向量div3,然后将其存储在程序中。

如果列表div3 是最新的,则输入应计入这些数字之一。如果它不能,那么它的任何因子都不包含“3”。如果它可以,则显示余数,可以使用常规方法进一步分解。

我认为这是“优化的”,因为首先检查了约束“任何因素都应包含 '3'”。只有找到任何个有效因子,你才需要计算所有其他的。

我的第一个程序使用<vector> 和它的同类,所以在你的 cmets 中要温柔:-)

(编辑)我现在注意到因子检查循环遍历整个div3 向量。当然,它只需要上升到number/2。留给读者作为练习。

(附加编辑)find3 在这里是一个 reverse 迭代器。出于某种似乎合适的原因,但我不记得我为什么这么认为了 :) 如果检查并包括 number/2,则需要将其更改为常规前向迭代器。

#include <iostream>
#include <vector>

using namespace std;

int contains_3 (int value)
{
    while (value && (value % 10) != 3)
        value /= 10;
    return value;
}

int main (int argc, char **argv)
{
    int number, found_flag, last_div3, adjust, adjust_digit;
    vector<int> div3;
    vector<int>::reverse_iterator find3;
    vector<int>::iterator it;

    // a little seeding
    div3.push_back(3);
    div3.push_back(13);
    div3.push_back(23);

    if (argc != 2)
        return -1;

    number = atoi (argv[1]);
    found_flag = 0;

    // do we need to expand div3?
    last_div3 = div3.back();

    while (last_div3 * 2 < number)
    {
    //  if this number contains a '3' in any other place than the last,
    //  simply increment it
        if ((last_div3 % 10) != 9 && contains_3(last_div3/10))
        {
            last_div3++;
        } else
        {
            // no? then simply pick the next multiple of 10 and add 3
            last_div3 /= 10;
            last_div3++;
            last_div3 *= 10;
            if (!contains_3(last_div3))
                last_div3 += 3;
        }
    //  check if it should be in the list
        for (it = div3.begin() ; it != div3.end() && (last_div3 % *it); ++it) ;
        if (it == div3.end())
        {
            div3.push_back(last_div3);
        }
    }

    cout << "list is now: ";
    for (it = div3.begin() ; it != div3.end(); ++it)
        cout << ' ' << *it;
    cout << endl;

    for (find3 = div3.rbegin(); !found_flag && find3 != div3.rend(); find3++)
    {
        if (!(number % *find3))
        {
            cout << "candidate: " << *find3 << ", remaining to sieve: " << number/(*find3) << endl;

            found_flag++;
        }
    }

    if (!found_flag)
        cout << "None found" << endl;

    return 0;
}

【讨论】:

  • 哈!我忘记了 n 的明显简单情况,其中 n 本身包含一个“3”(其对应的因子是“1”)。所以你可以使用我的contains_3 例程作为输入的第一个例程,如果它满足了约束。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2017-06-24
  • 2021-10-05
  • 1970-01-01
  • 2017-07-26
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多