Python 速成课程 15.10,使用 pygal 可视化随机游走

问题描述 投票:0回答:3

我正在阅读《Python 速成课程》这本书,我正在尝试使用 pygal 来可视化随机游走。(练习 15.10)。

这是我的代码:

from random import choice

class RandomWalk():
    """A class to generate random walks."""

    def __init__(self, num_points=500):
        """Initialize attributes of a walk."""
        self.num_points = num_points

        # All walks start at (0, 0).
        self.x_values = [0]
        self.y_values = [0]
        
    def get_step(self):
       
        direction = choice([1,-1])
        distance = choice([0, 1, 2, 3, 4])
        step = direction * distance
        return step
        
        
    def fill_walk(self):
        """Calculate all the points in the walk."""

        # Keep taking steps until the walk reaches the desired length.
        while len(self.x_values) < self.num_points:
            # Decide which direction to go and how far to go in that direction.

            x_step = self.get_step()
            y_step = self.get_step()

            # Reject moves that go nowhere.
            if x_step == 0 and y_step == 0:
                continue

            # Calculate the next x and y values.
            next_x = self.x_values[-1] + x_step
            next_y = self.y_values[-1] + y_step

            self.x_values.append(next_x)
            self.y_values.append(next_y)
            
#Visualizing with Pygal
import pygal

while True:
    rw = RandomWalk()
    rw.fill_walk()
    xy_chart=pygal.XY()
    xy_chart.title = 'Random Walk'
    rwValues=list(zip(rw.x_values,rw.y_values))
    xy_chart.add('rw',rwValues)
xy_chart.render_to_file('rw_visual.svg')

随机游走代码的逻辑很好,但是我似乎无法理解如何用 pygal 将其可视化。每当我运行代码(在 Jupyter 笔记本上)时,笔记本都不会处理它。我尝试用 matplotlib 对其进行可视化,一切都很好。如果有人能解释我做错了什么那就太好了。使用 matplotib 代码进行可视化是:

import matplotlib.pyplot as plt

# Keep making new walks, as long as the program is active.
while True:
    rw = RandomWalk()
    rw.fill_walk()
    plt.figure(figsize=(10, 10))
    point_numbers = list(range(rw.num_points))
    plt.plot(rw.x_values, rw.y_values,linewidth=1)
    plt.scatter(0, 0, c='green', edgecolors='none', s=100)
    plt.scatter(rw.x_values[-1], rw.y_values[-1], c='red', edgecolors='none',
        s=100)
    plt.axes().get_xaxis().set_visible(False)
    plt.axes().get_yaxis().set_visible(False)
    plt.show()
    keep_running = input("Make another walk? (y/n): ")
    if keep_running == 'n':
        break

运行得很好。

python python-3.x pygal
3个回答
1
投票

这是因为 Jupyter 默认情况下无法在输出单元上渲染

SVG
图像,因此您需要调整代码,以便
IPython
控制台可以读取它。您可以执行以下操作:

from IPython.display import HTML, display, SVG
import pygal

while True:
    rw = RandomWalk()
    rw.fill_walk()
    xy_chart = pygal.XY()
    xy_chart.title = 'Random Walk'
    rwValues = list(zip(rw.x_values, rw.y_values))
    xy_chart.add('rw', rwValues)
    keep_running = input("Make another walk? (y/n): ")
    if keep_running == 'n':
        display({'image/svg+xml': xy_chart.render()}, raw=True)
        # OR
        xy_chart.render_in_browser()
        # OR
        display(SVG(xy_chart.render(disable_xml_declaration=True)))
        break

1
投票

我现在只写了不到 3 个月的代码,但我认为你没有正确理解这个问题。

它说在 Ploty 上使用绘图随机游走(离线),我没有使用 pygal,所以我可能会回答一个没人问的问题,但无论如何我都会这样做。

由于书中的问题含糊不清,我将向您展示我是如何做到的。

from random import choice
from plotly.graph_objs import*
from plotly import offline


class RandomWalk:
    '''Generate random walks'''


    def __init__(self,points=5000):

        self.points = points


        #staring point is 0
        self.x_values =[0]
        self.y_values = [0]


    def fill_walk(self):

        '''calculating all of the points in the walk'''

        while len(self.x_values) < self.points:

            x_direction = choice([-1, 1])
            x_distance = choice([0, 3])
            x_step = x_direction * x_distance

            y_direction = choice([-1, 1])
            y_distance = choice([0, 3])
            y_step = y_direction * y_distance

            # reject all moves that go nowhere
            if x_step == 0 and y_step == 0:
                continue

            x = self.x_values[-1] + x_step
            y = self.y_values[-1] + y_step

            self.x_values.append(x)
            self.y_values.append(y)




rw = RandomWalk()
rw.fill_walk()

xa = list(range(rw.points))

frequencies = []

for a_number in (range(1,rw.points)):
    frequency = rw.x_values.count(a_number)
    frequencies.append(frequency)

data = [Bar(x=xa,y=frequencies)]

my_layout = Layout(title="We'll see",xaxis={'title':'X'},yaxis={'title':'Y'})

offline.plot({'data': data,'layout':my_layout},filename='my.html')

显示 y 值变化(频率 = rw.y_values.count(a_number)

我对代码感到抱歉,并且缺乏评论,这是我第一次发帖,但随着时间的推移,我会变得更好


0
投票

骰子:

from random import randint

class Die:
    def __init__(self,num_sides = 0):
        self.num_side = num_sides
    def roll(self):
        return randint(1,self.num_side)

使用 matplot lib 进行骰子可视化:

import matplotlib.pyplot as plt
from die import Die

die1 = Die(6)
die2 = Die(8)

result = []
frequency = []
max_num = (die1.num_side+die2.num_side)


for r in range(1,1000):
    result.append(die1.roll()+ die2.roll())
for value in range(2, max_num+1):
    frequency.append(result.append(value))

# its make me cunfuse but result loop make 1012 point instade of 999?
# i dont know whay but below calculation is the way come to my mind to 
# make sure both b in same size to can use scatter    
x_value = list (range(1,len(result)+1))

plt.style.use("bmh")
fig,ax = plt.subplots()
#ax.plot(result,c=(0.34,0.67,0.55),linewidth=3)
ax.scatter(x_value,result,c=result,cmap=plt.cm.Reds,
           edgecolor="none",s=3)
ax.get_xaxis().set_visible(False)
ax.get_yaxis().set_visible(False)

plt.show()

随机游走:

from random import choice

class RandomWalk:
    def __init__(self,num_points=5000):
        self.num_poins = num_points
        self.x_value = [0]
        self.y_value = [0]
    def fill_walk(self):
        while len(self.x_value) < self.num_poins:
            x_direction = choice([1,-1])
            x_distance = choice([0,1,2,3,4])
            x_point = x_direction* x_distance

            y_direction = choice([1,-1])
            y_distance = choice([0,1,2,3,4])
            y_point = y_direction* y_distance

            if x_point and y_point == 0:
                continue
            x = self.x_value[-1] + x_point
            y = self.y_value[-1] + y_point

            self.x_value.append(x)
            self.y_value.append(y)
        

用plotly可视化随机游走:

from plotly.graph_objects import Bar , Layout
from plotly import offline
from random_walk import RandomWalk 

rw = RandomWalk()
rw.fill_walk()

x_val
## Heading ##
ue = rw.x_value data = [Bar(x=x_val

ue,y=rw.y_value)]
x_value_config ={"title":"x value"}
y_value_config ={'title':"y value"}
my_layout = Layout(title="showing random walk",xaxis=x_value_config,
                   yaxis=y_value_config)
offline.plot({'data':data,'layout':my_layout},filename='rw.html')
© www.soinside.com 2019 - 2024. All rights reserved.