我正在使用此脚本从目录中的文件列表中进行采样,并且我正在使用种子
random.sample(population, k)
调用。
我希望在使用种子时使用
k=100
对 100 个项目进行采样,可以保证当我随后使用 k=800
进行采样时,这 100 个采样项目保证在 800 个采样项目的列表中。
但是,在某些目录中运行此脚本后,我得到的结果好坏参半。有时 100 在 800 之内,但有时几个文件存在差异,有些在这里,有些不在那里,反之亦然。
是否存在我不知道的随机性来源?
我尝试对
os.listdir()
调用进行排序,但这并没有改变任何内容。我知道我可以通过首先采样更大的值并切片样本列表来重构脚本以使其工作,但我希望我的原始脚本也能以相同的方式工作。
# script to sample from extracted frames from folders
import os
import random
import shutil
import argparse
def get_jpg_files(directory, ext="jpg"):
"""Get a list of all JPG files in a directory."""
dir_files = [f for f in os.listdir(directory)]
if ext:
dir_files = list(filter(lambda x: x.lower().endswith(f".{ext}"), dir_files))
print(f"Dir: {directory} - {len(dir_files)} files)")
return dir_files
def select_random_files(file_list, num_files, seed):
"""Randomly select a specified number of files from a list using a seed."""
random.seed(seed)
if num_files == -1:
num_files = len(file_list)
return random.sample(file_list, min(num_files, len(file_list)))
def copy_files(files, source_directory, destination_directory):
"""Copy selected files to the destination directory."""
if not os.path.exists(destination_directory):
os.makedirs(destination_directory)
for file in files:
shutil.copy(os.path.join(source_directory, file), destination_directory)
def main():
parser = argparse.ArgumentParser()
parser.add_argument("-i", "--input", help="Input dir", type=str)
parser.add_argument("-o", "--output",help="Output dir", type=str)
parser.add_argument("-n", "--num_files", help="Number of files to copy", type=int)
parser.add_argument("-e", "--ext", help="Copy only files with this extension", type=str, default=None)
args = parser.parse_args()
input_dir = args.input
output_dir = args.output
os.makedirs(output_dir, exist_ok=True)
SEED = 42
jpg_files = get_jpg_files(input_dir, ext=args.ext)
with open(f"/home/ik/shares/aiconstruction_workspace/TEST_SAMPLE/dir_files_{input_dir.split('/')[-1]}_{args.num_files}.txt", "w") as f:
f.write("\n".join(jpg_files))
selected_files = select_random_files(jpg_files, args.num_files, seed=SEED)
print(f"Selected files are: {selected_files}")
with open(f"/home/ik/shares/aiconstruction_workspace/TEST_SAMPLE/frames_{input_dir.split('/')[-1]}_{args.num_files}.txt", "w") as f:
f.write("\n".join(selected_files))
# copy_files(selected_files, input_dir, output_dir)
# print(f"Selected files from {input_dir}: {selected_files}")
if __name__ == "__main__":
main()
是否存在我不知道的随机性来源?
例如,对于不同的尺寸,算法本身可能会有所不同。特别是,请参阅 https://github.com/python/cpython/blob/main/Lib/random.py#L439 中的 if 。