将列表转换为十六进制字符串的优雅方法

4

我有一个长长的列表,看起来像这样:

[True, True, True, False, ... ]

在瓦片地图中代表墙壁。它的长度不保证是4的倍数,但如果在结尾处填充也没有关系。

我想将其转换为十六进制字符串,因此对于上面的示例,它将以E开头...

我希望有一种漂亮优雅的方法来实现这个(使用Python 2.7.3)!

谢谢。

编辑过的内容:

这是一个9x9地图的示例:

map = [True, True, True, True,
       True, True, True, True, 
       True, True, True, True, 
       True, False, False, True, 
       True, True, True, True, 
       True, False, False, False, 
       False, True, True, True, 
       True, True, False, False, 
       False, False, True, True, 
       True, True, True, True, 
       False, False, True, True, 
       True, True, True, True, 
       True, True, True, True, 
       True, True, True, True, 
       True, True, True, True, 
       True, True, True, True, 
       True, True, True, True, 
       True, True, True, True, 
       True, True, True, True, 
       True, True, True, True, 
       True]# False, False, False padded

我希望的是能够

str = heximify(map)
print str
> FFF9F87C3F3FFFFFFFFF8

我想你是指字节串,对吗? - Keith
不,实际上我想要一个字符串作为最终结果,类似于eff5ac5664abe。 - MalphasWats
如果长度不是4的倍数,您想要填充到哪里?您希望如何填充?或者换句话说,您能否展示一个输入长度为5时所需输出的示例? - Jon-Eric
答案在16小时前被标记为正确,问题在10小时前因不清楚而被搁置!有人得到了它! - MalphasWats
4个回答

7
通过位操作加入单行代码俱乐部,这似乎更为合适。
val = hex(reduce(lambda total, wall: total << 1 | wall, walls, 0))

这与以下代码的作用相同:
val = 0
for wall in walls:
    val <<= 1 # add one 0 bit at the "end"
    val |= wall # set this bit to 1 if wall is True, otherwise leave it at 0

val = hex(val) # get a hex string in the end
val = format(val, 'x') # or without the leading 0x if it's undesired

我觉得我可能很傻或者出了什么问题,那个结尾处的 print val 给我的结果是 0x1 - MalphasWats
@arshajii,tile是一个打字错误,实际上应该是wall(墙)。我编辑了回答以修正此错误。 - Jon-Eric
@arshajii 抱歉,我在我的代码中使用了 tiletiles,然后在将其与 OP 的命名匹配时错过了一个。感谢 Jon-Eric 进行修复。 - millimoose
@MalphasWats 我写的第二个例子是为了举例而没有测试,我会看一下它。如果我正确理解你的问题,第一个应该是正确的。 - millimoose
@MalphasWats 对的,我漏掉了 <<= - millimoose
显示剩余2条评论

4
>>> walls = [True, True, True, False]
>>> hex(int(''.join([str(int(b)) for b in walls]), 2))
'0xe'

或者(受@millimoose回答的启发),
>>> hex(sum(b<<i for i,b in enumerate(reversed(walls))))
'0xe'

2
walls = [True, True, True, False, ... ]
val = 0
for w in walls:
    val *= 16
    val += int(w)
val = hex(val) 

或者一个简单的一行代码:
val = hex(sum(i*16**pow for i,pow in zip((int(w) for w in walls),range(len(walls))[::-1])))

我喜欢这个(顶部)的外观,但是val最终变成了0x1110而不是E。 - MalphasWats
@MalphasWats:如果没有一个示例,我实在无法进行调试。或者也许我误解了你的问题。 - inspectorG4dget
我更新了我的问题,抱歉。 - MalphasWats

0
>>> hex(int("".join(["%d"%s for s in [True,True,True,False]]),2))
'0xe'

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接