Arrays Perl从随机填充的数组计算平均值

Arrays Perl从随机填充的数组计算平均值,arrays,perl,Arrays,Perl,我有一个学校作业需要帮助。现在,我知道你在想什么,但是我的老师不在城里,没有回复我的电子邮件,我的其他同学也不知道如何解决这个问题。一些建议和提示将不胜感激 任务如下: 我们应该创建一个数组,用20到30个1-100范围内的随机整数填充它。然后,借助子程序,我们应该计算这些数字的平均值 这个问题发生在我调用子程序的时候,它要么给我答案0,要么给我“非法除以0”的错误。我现在掌握的代码是: #! /usr/bin/perl -w use warnings; use strict; # Decl

我有一个学校作业需要帮助。现在,我知道你在想什么,但是我的老师不在城里,没有回复我的电子邮件,我的其他同学也不知道如何解决这个问题。一些建议和提示将不胜感激

任务如下:

我们应该创建一个数组,用20到30个1-100范围内的随机整数填充它。然后,借助子程序,我们应该计算这些数字的平均值

这个问题发生在我调用子程序的时候,它要么给我答案0,要么给我“非法除以0”的错误。我现在掌握的代码是:

#! /usr/bin/perl -w

use warnings;
use strict;

# Declaring the scalar variables and arrays.
my @AllNumbers;

# Create random data set of between 20 to 30 measures used for the 100 random intigers.
my $random_number = int( rand( 31 - 20 ) ) + 20;

# Create random data set of 100 intigers.
for ( my $i = 0 ; $i <= $random_number ; $i++ ) {
    $AllNumbers[$i] = int( rand( 100 - 1 ) );
}

# Print the 20 to 30 random numbers (range 1 - 100).
print("Your random numbers are: \n@AllNumbers");

sub average {
    my $ArrayAverage = @_;
    for (@_) {
        my $total += $_;
    }
    return $ArrayAverage / $random_number;
} ## end sub average

# Print the mean/average of the 20-30 numbers.
print( "\n\nThe average of those random numbers is: ", &average, "\n\n" );
#/usr/bin/perl-w
使用警告;
严格使用;
#声明标量变量和数组。
我的@allnumber;
#创建用于100个随机计数器的20到30个测量值的随机数据集。
我的$random_number=int(兰特(31-20))+20;
#创建100个初始化器的随机数据集。

(我的$i=0;$i干得好,你在请求帮助之前自己试过了

要调试代码,请尝试添加一些打印,以尽量减少需要查找错误的区域。因此,在这种情况下,您可以在average sub中添加
print$random\u number
,您会注意到它设置正确。而如果打印$ArrayAverage的元素,您会发现它没有值,这只是因为在脚本最后一行的打印中调用@AllNumbers数组时,需要将它传递给&average子数组

因此,解决方案是在调用时只需将@AllNumbers数组传递给&average():

print(“\n\n这些随机数的平均值是:”,&average(@AllNumbers),“\n\n”);


这应该行得通;)祝你好运

到目前为止,干得不错!差不多可以了。但是您调用的是平均函数,而不是 任何参数(
&average
)。试着这样做:

sub average{
    my @Array_To_Average = @_; # this is now a local copy of the global @AllNumbers
    my $total = 0;
    for (@Array_To_Average) # iterate over the local copy ...
    { 
        $total += $_; # ...and sum up
    }
    return $total / $random_number;

    # instead of $random_number you could also use
    # scalar(@Array_To_Average). That's the number of items
    # in the array, i.e.
    #   return $total / scalar(@Array_To_Average);
}

print ("\n\nThe average of those random numbers is: ", average(@AllNumbers), "\n\n");
调用函数时请省略
&
。那是非常古老的风格。 喜欢大多数其他语言中使用的样式:

my $result1 = some_function();
my $result2 = some_other_function($param1, $param2);
(主要)问题是,您调用sub时没有参数! 试试这个:

average($_) foreach @AllNumbers;

my $count = 0;
my $total;
my $average;

sub average{
    my $num = shift;
    $count++; # count number of random numbers 
    $total += $num; # sum up
    $average = $total/$count; # calculate average
    return $average;
}

# Print the mean/average of the 20-30 numbers.
print ("\n\nThe average of those random numbers is: ", $average, "\n\n");

让它发挥作用来帮助你

#! /usr/bin/perl -w

use warnings;
use strict;

# Declaring the scalar variables and arrays.
my @AllNumbers;
my $avgOfArray;

# Create random data set of between 20 to 30 measures used for the 100         random intigers.
my $random_number = int(rand(31 - 20)) + 20;

# Create random data set of 100 intigers.
for(my $i = 0; $i <= $random_number; $i++){
    $AllNumbers[$i] = int(rand(100 - 1));
}

# Print the 20 to 30 random numbers (range 1 - 100).
print ("Your random numbers are: \n@AllNumbers");
sub average {
    my @array = @_; # save the array passed to this function
    my $sum; # create a variable to hold the sum of the array's values
    foreach (@array) { $sum += $_; } # add each element of the array
    # to the sum
    return $sum/@array; # divide sum by the number of elements in the
    # array to find the mean
}
$avgOfArray = average(@AllNumbers);

# Print the mean/average of the 20-30 numbers.
print ("\n\nThe average of those random numbers is: ",  $avgOfArray,     "\n\n"); here
#/usr/bin/perl-w
使用警告;
严格使用;
#声明标量变量和数组。
我的@allnumber;
我的$avgOfArray;
#创建用于100个随机计数器的20到30个测量值的随机数据集。
我的$random_number=int(兰特(31-20))+20;
#创建100个初始化器的随机数据集。

对于(my$i=0;$i),我首先要指出几个风格点:

    >P>把你的SUP放在开始(或者如果你必须,在最后)。把它放在代码的中间是凌乱的。

  • 不要用
    &
    调用子例程-这是一种不好的风格,会导致一些奇怪的行为。在您的情况下:
    &average
    实际上是在没有参数的情况下被调用的。不过,一般来说这是不好的,除非您明确知道为什么要这样做,否则不要使用它。(它确实有一些用途,但当你看到它们时你就会知道——而且你在早期学习
    perl
    时不会知道)

  • 这种数组的大写形式并不好,因为模块/包就是这样命名的。如果可以,请使用小写变量

  • for循环是一个C风格的循环,它可以工作,但是最好是为(1..$random_number){
编写
,因为您不需要迭代器

  • 您不需要在shebang行中使用
    -w
    ,因为您有
    使用警告
    使用警告;
    是更好的方法

  • 调用变量
    $random\u number
    没有多大帮助-我们可以看到这一点,因为它为
    rand
    分配了结果。按它的用途命名-比如
    $number\u元素

  • 考虑到您只需要使用一次
    $random\u number
    ,您可能不需要将其固定在变量中。如果您觉得它有助于可读性,您可以这样做(这是品味的问题——在好的编程中,清晰易读是唯一真正重要的事情——考虑到当今编译器的状态,大多数内存/性能方面的事情都是过早的优化。)

  • 但你的核心问题是:

    my $ArrayAverage = @_;
    
    这将
    $ArrayAverage
    设置为列表中的元素数。这将始终与
    $random\u number
    相同,因为这是您迭代的次数

    您在这里迭代元素,但实际上不使用
    $total

    for (@_) {
        my $total += $_;
    }
    
    这里-返回数组中的元素数除以数组中的元素数

    return $ArrayAverage / $random_number;
    
    但真正重要的是——这些都不重要,因为你调用它时使用的是
    &average
    ,它实际上并没有发送任何参数。所以你只是输入零,输出零

    了解这一点可能很有用-标量上下文中的数组返回元素数,因此计算平均值非常简单:

    my $sum; 
    $sum += $_ for @AllNumbers; 
    print( "\n\nThe average of those random numbers is: ", $sum / @AllNumbers, "\n\n" );
    
    这将产生一个长的十进制数-如果需要格式化它,可以使用
    printf
    sprintf

    printf( "\n\nThe average of those random numbers is: %02.2f \n\n", $sum / @AllNumbers);
    
    因此,我将稍微重写如下:

    #!/usr/bin/perl
    
    use warnings;
    use strict;
    
    # Declaring the scalar variables and arrays.
    my @all_numbers;
    
    
    #repeat 20 + random 11 times - so 20-30
    for ( 1 .. 20 + int rand 11 ) { 
        push ( @all_numbers, int rand 99 );
    }
    
    # Print the 20 to 30 random numbers (range 1 - 100).
    print("Your random numbers are: \n@all_numbers\n");
    
    #calculate sum of elements
    my $sum; 
    $sum += $_ for @all_numbers;
    
    print "Sum: $sum count: ", scalar @all_numbers, "\n"; 
    
    # Print the mean/average of the 20-30 numbers.
    printf( "\n\nThe average of those random numbers is: %02.2f \n\n", $sum / @all_numbers);
    

    用惯用的Perl编写它会得到如下结果:

    #!/usr/bin/perl
    
    use warnings;
    use strict;
    
    my @numbers;
    
    my $how_many = int(rand 11) + 20;
    
    push @numbers, int(rand 100) + 1 for 1 .. $how_many;
    
    print "Your random numbers are: \n@numbers\n";
    print "The mean of those numbers is: ", average(@numbers), "\n";
    
    sub average{
      my $total;
      $total += $_ for @_;
      return sprintf '%.2f', $total / @_;
    }
    

    您需要将参数传递给
    average
    子例程:

    #!/usr/bin/perl
    
    sub average{
      my $tot;
      $tot += $_ for @_;
      return sprintf '%.3f', $tot / @_;
    }
    my @num;
    
    my $quantity = int(rand 11) + 20;    
    push @num, int(rand 100) + 1 for 1 .. $quantity;
    
    print "Random numbers: \t@num\n";
    print "Average: ", average(@num), "\n";
    

    顺便说一句,如果你需要@AllNumbers的覆盖范围是1-100,你应该用另一种方式来完成。因为这
    rand(100-1)
    rand(99)
    相同,后者给你的覆盖范围是0-98。你需要进一步研究并修复它;)在堆栈溢出问题上不禁止家庭作业帮助。只是我们会帮助您理解它(并解决问题),而不是帮您做。非常感谢您的帮助!我不敢相信我错过了。另外,关于
    标量(@Array\u To\u Average)的好提示
    ,我不知道这是一件事…
    如果需要强制执行,则需要标量