"ValueError: too many values to unpack (expected 3)"

i am working through totter333’s networked game tutorial on youtube (https://www.youtube.com/watch?v=A-OY1h_iPl4), and i am running the following code in his example file


import bge
cont = bge.logic.getCurrentController()
owner = cont.owner
if cont.sensors['run'].positive:
    connection, ping, players = bge.network.run()
    owner['ping'] = ping
    owner['players'] = players
    owner['connection'] = connection

i get the following error:


File "run network.py", line 5, in <module>
    connection, ping,players = bge.network.run()
ValueError: too many values to unpack (expected 3)

i googled this error and found nothing specific to blender, but lots of stuff about python generally where people needed to “split” something, usually by adding .split(",") to the end of an input string. so i gave that try, changing line 5 of the code to:


    connection, ping, players = bge.network.run().split(",")

but then i got this error:


File "run network.py", line 5, in <module>
    connection, ping,players = bge.network.run()
AttributeError: 'tuple' object has no attribute 'split'

any help here? if it matters, i’m running mac os x with python 3.4, but totter333 assumes you have python 3.2.

(sorry i didn’t contact totter333 directly but i couldn’t find an e-mail address)

sounds like your recalling data, that is a list, not a tuple
the data your accessing needs to be (value,value,value)

It doesn’t have to be a tuple. It just needs to match the pattern: 3 elements for 3 variables.

BTW:


@theOtherHolmes

Try this:

connection, ping, players, *_ = bge.network.run()

Also, you might want to give this networking tutorial a try: http://www.youtube.com/watch?v=4xZRfzOtxzA

1 Like

thanks, now that i’m digging line by line into totter333’s code behind line 5, specifically, behind bge.network.run(), and it looks like this – the very last line (return line) is what caught my attention—


def run(self):
        size = 0
        if self.connection == "connected":
            #print(self.localNetObjects[str(self.clientID)+str(":")+str(0)].gameObject['ID'])
            #self.handleDeletedObjects()
            self.syncLocalGhosts()
            self.sendGameState()
            self.setConnectedClients()
            result,size = self.recvGameState()
            if result != False:
                self.gameState = result
                self.handleDeletedGhosts()
                self.handleConnections()
                self.setPing()
                self.updateScene()
                #print(str("true")+str(size))
            else:
                #print("false")
                self.timeout = time.time()
        
            if self.timeout >= self.maxTimeout:
                print("socket timed out")
                self.disconnect()
        
        return (self.connection,self.ping,len(self.gameState),size)

i know this is probably partly meaningless without being able to look at all the other code, but does it matter that the return line is returning four values instead of three? after all, the original error says ‘(expected 3)’

is this significant, or am i misunderstanding the return line?

Indeed it’s returning four values, yet the tuple unpacking asks for a sequence of only three. Whilst I commend you on approaching the subject of programming and networking, it would be wise to learn why / how python objects have certain methods and not others. You can imply the available methods and attributes of a python object by looking at its type.

Python functions can return multiple variables . These variables can be stored in variables directly. This is a unique property of Python , other programming languages such as C++ or Java do not support this by default.

The valueerror: too many values to unpack occurs during a multiple-assignment where you either don’t have enough objects to assign to the variables or you have more objects to assign than variables. If for example myfunction() returned an iterable with three items instead of the expected two then you would have more objects than variables necessary to assign to.