Python 列表索引方法在 class 中表现异常
Python list index method behaves strange inside a class
我有一个简单的 class,其中一种方法是获取指定值列表的索引,前提是它包含该值。
方法就是下面class中的get_index_at_time(时间)
class TimeStamp:
def __init__(self):
self.timeList = []
self.indexList = []
self.localDate = None
def add(self, inTime, idx):
if self.localDate is None:
# Get todays date
self.localDate = datetime.datetime.now()
# Fix timeList with time adjusted to inTime
thisTime = create_timestamp(self.localDate, inTime)
self.timeList.append(thisTime)
self.indexList.append(idx)
def get_time_at_index(self, ix):
if len(self.timeList) > ix and 0 <= ix:
return self.timeList[ix]
def get_index_at_time(self, inTime):
ix = self.timeList.index(inTime)
if ix:
return self.indexList[ix]
else:
return -1
对于列表中的第一个元素,由于某些奇怪的原因,这失败了,例如index 0 但我已经检查过具有相同数据的列表上的 index 方法是否适用于 index 0 它只有在 class 内部使用时才会表现得很奇怪。
运行 脚本给出了这个:
$ python3 simple_index_test.py
====================================================
Testing list index method for dbgList:
Test passed
====================================================
Start testing TimeStamp.get_time_at_index
Test passed
====================================================
Start testing TimeStamp.get_index_at_time
- Test Failed for time stamp: 2020-04-12 01:01:01
====================================================
Comparing the values in dbgList with idx1.TimeList
Test passed
====================================================
代码如下:
import datetime
def create_timestamp(localDate, inTime):
timeString = localDate.strftime('%Y-%m-%d') + ' ' + inTime
return datetime.datetime.strptime(timeString, '%Y-%m-%d %H:%M:%S')
class TimeStamp:
def __init__(self):
self.timeList = []
self.indexList = []
self.localDate = None
def add(self, inTime, idx):
if self.localDate is None:
# Get todays date
self.localDate = datetime.datetime.now()
# Fix timeList with time adjusted to inTime
thisTime = create_timestamp(self.localDate, inTime)
self.timeList.append(thisTime)
self.indexList.append(idx)
def get_time_at_index(self, ix):
if len(self.timeList) > ix and 0 <= ix:
return self.timeList[ix]
def get_index_at_time(self, inTime):
ix = self.timeList.index(inTime)
if ix:
return self.indexList[ix]
else:
return -1
log1 = [
[0.123, '01:01:01', 0],
[0.134, '01:01:02', 1],
[0.145, '01:01:03', 1],
[0.156, '01:01:04', 2],
[0.167, '01:01:05', 2],
[0.178, '01:01:06', 2],
[0.189, '01:01:07', 3],
]
def main():
# Get todays date
localDate = datetime.datetime.now()
idx1 = TimeStamp()
# debug list for testing the index method directly
dbgList = []
# Fill idx1
for ix,val in enumerate(log1):
idx1.add(val[1], ix)
# Debugging why test fails, create an identical list of same time stamp as in the TimeStamp class
thisTime = create_timestamp(localDate, val[1])
dbgList.append(thisTime)
print('====================================================')
print('Testing list index method for dbgList:')
testPassed = True
for ix, val in enumerate(dbgList):
rx = dbgList.index(val)
if rx != ix:
print('List index() method failed match for: ' + str(val))
testPassed = False
if testPassed:
print('Test passed')
# Test method get_time_at_index
print('====================================================')
print('Start testing TimeStamp.get_time_at_index')
testPassed = True
# Loop over all elements in log1
for ix,val in enumerate(log1):
thisTime = idx1.get_time_at_index(ix)
# Create the expected time stamp
expectedTime = create_timestamp(localDate, val[1])
if thisTime != expectedTime:
print(' - Test Failed for index: ' + str(ix))
testPassed = False
if testPassed:
print('Test passed')
# Test method get_index_at_time
print('====================================================')
print('Start testing TimeStamp.get_index_at_time')
testPassed = True
# Loop over all elements in log1
for ix,val in enumerate(log1):
# Create the time we want to get index for
wantedTime = create_timestamp(localDate, val[1])
thisIndex = idx1.get_index_at_time(wantedTime)
if thisIndex != ix:
print(' - Test Failed for time stamp: ' + str(wantedTime))
testPassed = False
if testPassed:
print('Test passed')
print('====================================================')
print('Comparing the values in dbgList with idx1.TimeList')
testPassed = True
for ix, val in enumerate(dbgList):
idxTimeStamp = idx1.timeList[ix]
if idxTimeStamp != val:
print(' - Test Failed for time stamps (dbg) (idx1.timeList): ' + str(val) + ' ' + str(idxTimeStamp))
testPassed = False
if testPassed:
print('Test passed')
print('====================================================')
if __name__ == "__main__":
main()
我发现这个问题刚好发生在第一个索引 (index-0) 上。如果您打印 thisIndex
(at testing TimeStamp.get_index_at_time) variabel,那么第一个循环将是 -1
。
查看您的 get_index_at_time()
函数。发生这种情况是因为 if
语句将为 0
return False
。因此,该函数将 return -1
。你可以修复为 if 添加一个条件。我们开始吧:
def get_index_at_time(self, inTime):
ix = self.timeList.index(inTime)
if ix or ix == 0:
return self.indexList[ix]
else:
return -1
输出将是:
====================================================
Testing list index method for dbgList:
Test passed
====================================================
Start testing TimeStamp.get_time_at_index
Test passed
====================================================
Start testing TimeStamp.get_index_at_time
Test passed
====================================================
Comparing the values in dbgList with idx1.TimeList
Test passed
====================================================
(抱歉英语不好)
我有一个简单的 class,其中一种方法是获取指定值列表的索引,前提是它包含该值。 方法就是下面class中的get_index_at_time(时间)
class TimeStamp:
def __init__(self):
self.timeList = []
self.indexList = []
self.localDate = None
def add(self, inTime, idx):
if self.localDate is None:
# Get todays date
self.localDate = datetime.datetime.now()
# Fix timeList with time adjusted to inTime
thisTime = create_timestamp(self.localDate, inTime)
self.timeList.append(thisTime)
self.indexList.append(idx)
def get_time_at_index(self, ix):
if len(self.timeList) > ix and 0 <= ix:
return self.timeList[ix]
def get_index_at_time(self, inTime):
ix = self.timeList.index(inTime)
if ix:
return self.indexList[ix]
else:
return -1
对于列表中的第一个元素,由于某些奇怪的原因,这失败了,例如index 0 但我已经检查过具有相同数据的列表上的 index 方法是否适用于 index 0 它只有在 class 内部使用时才会表现得很奇怪。
运行 脚本给出了这个:
$ python3 simple_index_test.py ==================================================== Testing list index method for dbgList: Test passed ==================================================== Start testing TimeStamp.get_time_at_index Test passed ==================================================== Start testing TimeStamp.get_index_at_time - Test Failed for time stamp: 2020-04-12 01:01:01 ==================================================== Comparing the values in dbgList with idx1.TimeList Test passed ====================================================
代码如下:
import datetime
def create_timestamp(localDate, inTime):
timeString = localDate.strftime('%Y-%m-%d') + ' ' + inTime
return datetime.datetime.strptime(timeString, '%Y-%m-%d %H:%M:%S')
class TimeStamp:
def __init__(self):
self.timeList = []
self.indexList = []
self.localDate = None
def add(self, inTime, idx):
if self.localDate is None:
# Get todays date
self.localDate = datetime.datetime.now()
# Fix timeList with time adjusted to inTime
thisTime = create_timestamp(self.localDate, inTime)
self.timeList.append(thisTime)
self.indexList.append(idx)
def get_time_at_index(self, ix):
if len(self.timeList) > ix and 0 <= ix:
return self.timeList[ix]
def get_index_at_time(self, inTime):
ix = self.timeList.index(inTime)
if ix:
return self.indexList[ix]
else:
return -1
log1 = [
[0.123, '01:01:01', 0],
[0.134, '01:01:02', 1],
[0.145, '01:01:03', 1],
[0.156, '01:01:04', 2],
[0.167, '01:01:05', 2],
[0.178, '01:01:06', 2],
[0.189, '01:01:07', 3],
]
def main():
# Get todays date
localDate = datetime.datetime.now()
idx1 = TimeStamp()
# debug list for testing the index method directly
dbgList = []
# Fill idx1
for ix,val in enumerate(log1):
idx1.add(val[1], ix)
# Debugging why test fails, create an identical list of same time stamp as in the TimeStamp class
thisTime = create_timestamp(localDate, val[1])
dbgList.append(thisTime)
print('====================================================')
print('Testing list index method for dbgList:')
testPassed = True
for ix, val in enumerate(dbgList):
rx = dbgList.index(val)
if rx != ix:
print('List index() method failed match for: ' + str(val))
testPassed = False
if testPassed:
print('Test passed')
# Test method get_time_at_index
print('====================================================')
print('Start testing TimeStamp.get_time_at_index')
testPassed = True
# Loop over all elements in log1
for ix,val in enumerate(log1):
thisTime = idx1.get_time_at_index(ix)
# Create the expected time stamp
expectedTime = create_timestamp(localDate, val[1])
if thisTime != expectedTime:
print(' - Test Failed for index: ' + str(ix))
testPassed = False
if testPassed:
print('Test passed')
# Test method get_index_at_time
print('====================================================')
print('Start testing TimeStamp.get_index_at_time')
testPassed = True
# Loop over all elements in log1
for ix,val in enumerate(log1):
# Create the time we want to get index for
wantedTime = create_timestamp(localDate, val[1])
thisIndex = idx1.get_index_at_time(wantedTime)
if thisIndex != ix:
print(' - Test Failed for time stamp: ' + str(wantedTime))
testPassed = False
if testPassed:
print('Test passed')
print('====================================================')
print('Comparing the values in dbgList with idx1.TimeList')
testPassed = True
for ix, val in enumerate(dbgList):
idxTimeStamp = idx1.timeList[ix]
if idxTimeStamp != val:
print(' - Test Failed for time stamps (dbg) (idx1.timeList): ' + str(val) + ' ' + str(idxTimeStamp))
testPassed = False
if testPassed:
print('Test passed')
print('====================================================')
if __name__ == "__main__":
main()
我发现这个问题刚好发生在第一个索引 (index-0) 上。如果您打印 thisIndex
(at testing TimeStamp.get_index_at_time) variabel,那么第一个循环将是 -1
。
查看您的 get_index_at_time()
函数。发生这种情况是因为 if
语句将为 0
return False
。因此,该函数将 return -1
。你可以修复为 if 添加一个条件。我们开始吧:
def get_index_at_time(self, inTime):
ix = self.timeList.index(inTime)
if ix or ix == 0:
return self.indexList[ix]
else:
return -1
输出将是:
====================================================
Testing list index method for dbgList:
Test passed
====================================================
Start testing TimeStamp.get_time_at_index
Test passed
====================================================
Start testing TimeStamp.get_index_at_time
Test passed
====================================================
Comparing the values in dbgList with idx1.TimeList
Test passed
====================================================
(抱歉英语不好)