【问题标题】:Python choose random number in specific intervalPython在特定区间内选择随机数
【发布时间】:2019-07-16 23:41:36
【问题描述】:

所以我正在制作一个 PyGame,棒球从上往下掉,底部的用户必须接住球。球以随机的速度下落,但我很难让球以不同的速度下落。

例如,我当前的球代码是:

def update(self):
    if self.is_falling:
        """Move the ball down."""
        self.y += random.randint(10, 200) / 100
        self.rect.y = self.y

在这里,当我运行程序时,球以不同的速度下落,但几乎没有什么不同。如果我将数字更改为 (10, 20000) / 100,那么每个球的下落速度都非常快。原因是什么?似乎随机数不是那么随机。我是不是用错了函数?

我想让每个球以非常不同的速度下落,比如一个非常快,另一个非常慢。而且我希望它是随机数,以便用户可以以多种不同的速度玩...

我想知道,是否有随机函数可以在生成的随机数之间设置特定间隔?还是我应该尝试不同的方法?如果是这样,我该怎么做?

我是Python的初学者,所以如果你能尽可能简单地解释一下,那将不胜感激!

【问题讨论】:

  • 尝试使用import random; speed = random.random() * 15 或类似的东西。 random.random() 返回一个介于 0 和 1 之间的数字,您可以将其乘以您想要的最大数字!
  • @Reedinationer 所以我尝试了这种方法,但我仍然得到相同的结果。如果像random.random() *2 那样做让它变慢,所有的球都在减速,但差别很小。如果我像random.random()*15 那样做,那么所有的球都会变得更快,但同样,速度也略有不同。
  • 将下落速度存储在某处,以查看它们的实际差异。错误可能完全在其他地方。
  • @Sam 实际上,这是个好主意。我开始认为随机函数很奇怪,但它可能是我的全部。谢谢!
  • @Sarah 首先,random.random()*15 返回一个介于 0 和 15 之间的数字,因此它可能会将速度提高 0.00001,而您只知道您是否要使用 print() 的值。其次,它取决于初始速度的规模。如果你的球是 300 并且你将它增加 0.5 你不会注意到它。如果它是 0.5 并且你将它增加 15 它将使你的游戏无法玩。由您来微调这些参数

标签: python random pygame


【解决方案1】:

稍微调整一下数字,20000 比 200 跳得非常大。因为您现在得到的值是 10/100 和 200/100。这是 0.1 到 2 像素,所以我不认为它们会有很大不同。你跳到 10/100 到 20000/100,这是一个巨大的速度,与原来的 2 相比大约是 200 像素上限。所以这就是你的问题。可能是 200 到 2000 甚至 200 到 2500 的范围。你不需要像你说的那样大的调整,球开始很快下落。我以前做过同样的游戏,我可以说你只需要稍微调整一下数字。

【讨论】:

    【解决方案2】:

    部分问题是亚像素距离。我认为您的主要问题是您的y 运动。查看self.y += 的等式,一半的时间将导致像素距离只有一个像素。当它被添加到 self.rect 时,四舍五入(或截断)将使小于 1 像素的数量消失。比如生成的随机整数是99,然后除以100,就是0.99个像素。在 python 中,int(0.99) 为零。因此,大约一半的时间,移动为零,另一半,移动只有 1 个像素,因为int(150/100) => 1。 (每约 190 个时刻中有一个是 2 个像素。)

    def update(self):
        if self.is_falling:
            """Move the ball down."""
            self.y += random.randint(10, 200) / 100
            self.rect.y = self.y
    

    正如@6502 指出的那样,这会产生不规则的随机运动。最好在 __init__ 类中生成像素更新速度,并坚持下去。

    def __init__( self, ... ):
        ...
        self.fall_speed = random.randint(10, 200)   # pixels per update
    
    def update(self):
        if self.is_falling:
            """Move the ball down."""
            self.y += self.fall_speed
            self.rect.y = self.y
    

    我喜欢根据实时计算让事物移动。这需要对象速度和帧间时间来计算对象移动了多少。我喜欢这个,因为如果你想在程序中添加重力(或其他),计算新位置很容易。

    class FallingSprite( pygame.sprite.Sprite ):
        """ A falling sprite.  Falls at a constant velocity in real-time """
        def __init__( self, image ):
            pygame.sprite.Sprite.__init__( self )
            self.image       = image
            self.rect        = self.image.get_rect()
            self.fall_speed  = random.randint(10, 200) # pixels / second
            self.last_update = int( time.time() * 1000.0 )
            self.rect.center = ( random.randrange( 0, WINDOW_WIDTH ), 0 )  
    
        def update( self ):
            # There may have been movement since the last update
            # so calculate the new position (if any)
            if ( self.fall_speed > 0 ):
                time_now    = int( time.time() * 1000.0 )
                time_change = time_now - self.last_update      # How long since last update?
                if ( time_change > 0 ):
                    distance_moved   = time_change * self.fall_speed / 1000
                    now_x, now_y     = self.rect.center        # Where am I, right now
                    updated_y        = now_y + distance_moved
                    # Did we fall off the bottom of the screen?
                    if ( updated_y > WINDOW_HEIGHT ):
                        # sprite disappears
                        self.kill()
                    else:
                        self.rect.center = ( now_x, updated_y )
                        self.last_update = time_now
    

    【讨论】:

    • 哇。非常感谢您的详细回答。我一定会以它为指导,然后再试一次!
    【解决方案3】:

    如果这是 Python 2,则存在问题

    random.randint(10, 200) / 100
    

    因为除法将在整数数学中完成。 你应该使用

    random.randint(10, 200) / 100.
    

    另一个问题是,您在每次更新(可能是每一帧)时都选择了随机步长,这不会给人一种速度的错觉,而是更多的随机抖动运动。 最好选择像您正在做的随机速度,但至少在几帧甚至整个秋季动画中保持相同。

    【讨论】:

    • 我使用的是最新版本的python,我相信它是3.7...?
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2016-08-14
    • 1970-01-01
    • 2019-06-06
    • 1970-01-01
    相关资源
    最近更新 更多