Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/python/355.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Python Django web应用程序的复杂编码逻辑_Python_Django_Python 2.7_Django Views - Fatal编程技术网

Python Django web应用程序的复杂编码逻辑

Python Django web应用程序的复杂编码逻辑,python,django,python-2.7,django-views,Python,Django,Python 2.7,Django Views,我有一些特殊的需求,我正试图找出编写它的最佳方法。最重要的是效率,其次是可维护性。要求是这样的(请容忍我): 我的Django网站上有一个功能,旨在为注册用户和未注册用户提供服务。这项功能将在每个用户的pin码后面设置门控。我要求随机生成这些管脚(而不是串行生成) pin码需要令人难忘-这意味着pinlen成为一个因素。我想要一个4位数的pin码。因为字母数字比纯数字更难记忆(根据我进行的可用性测试,我坚持这些结果) 我不能在pin码之间发生冲突,因为它们也将被用作标识符——所以它们都必须是唯一

我有一些特殊的需求,我正试图找出编写它的最佳方法。最重要的是效率,其次是可维护性。要求是这样的(请容忍我):

我的Django网站上有一个功能,旨在为注册用户和未注册用户提供服务。这项功能将在每个用户的pin码后面设置门控。我要求随机生成这些管脚(而不是串行生成)

pin码需要令人难忘-这意味着pin
len
成为一个因素。我想要一个4位数的pin码。因为字母数字比纯数字更难记忆(根据我进行的可用性测试,我坚持这些结果)

我不能在pin码之间发生冲突,因为它们也将被用作标识符——所以它们都必须是唯一的。我的范围将在0000到9999之间。只有10K的独特组合是可能的。这是有限制的,但pin码的可记忆性比可能的pin码池的大小具有更高的优先级。所以我要牺牲

最后,注册用户的pin码将被永久分配。另一方面,未注册的用户将被分配不超过24小时的PIN,在这24小时后,他们将过期,因此再次进入未使用PIN池

假设我的上述数据模型(在
models.py
中)是这样的:

class Inbox(models.Model):
    pin_code = models.CharField(default='0')
    owner = models.ForeignKey(User)
    creation_time = models.DateTimeField(auto_now_add=True)
views.py
中,我需要一种方法将可用的
pin_代码
分配给我创建的每个
Inbox
对象。最有效的逻辑是什么?以下是我如何看待它的:

def expire_pin(time_difference=None):

    #admin user (with id 1) is assumed as the 'unregistered user'
    Inbox.objects.filter(creation_time__lte=time_difference,owner_id=1).update(pin_code='0')

def get_pin():

    parent_list = ['{:04d}'.format(i) for i in range(10000)]
    day_ago = timezone.now() - timedelta(hours=24)
    expire_pin(day_ago)
    to_exclude = Inbox.objects.filter(~Q(pin_code='0')).values_list('pin_code',flat=True)
    new_list = [item for item in parent_list if item not in to_exclude]
    return random.choice(new_list)

可选:您不必阅读它,但以下是我使用
pin\u代码的目的。每个已注册和未注册的用户都分配了一个收件箱,可在
example.com/pin/XXXX
XXXX
pin\u代码
)访问。用户可以通过社交媒体与其朋友共享此收件箱地址。朋友们可以通过他们的手机号码登录,查看前用户留给这位朋友的内容。明白了吗

我需要为已注册和未注册的用户提供此功能-因此需要为未知用户分配
pin_代码。但我希望能够回收未注册的用户代码,这样我就不会太快用完10K的可能性。我在这个网站上有一个相当大的用户群


不过,最终我会用完10K组合。我想我会写代码,然后无缝转换到5位数的引脚。但即使在这种情况下,如果任何4位PIN过期并可用,它们将在分配期间获得第一优先权。如果你也能帮我,那就太好了

这是一个很好的故事,但我不能100%确定你的问题是什么。如何生成随机数

import random
print('%04d' % random.randint(0, 10000))
将其放入while循环中,以确保它还不存在于数据库中。或者,使用
used
布尔值在数据库中预生成10000个pin码的列表,以获得稍微更有效的解决方案



我不得不问,记住真的是一个要求吗?如果是,自定义字符串不是更好的主意吗?随机数并不是那么容易记住的,人们更善于记住自己想的东西。

对于pin码分配;我相当肯定您的代码也在做类似的事情:

首先,我将保留一个所有代码可能性的列表(最好现在创建该列表),因此将是一个简单的表: 唯一的4位代码:指定的布尔值

然后我将创建一个函数:

sudo代码:

def new_pin(db_list):
    # db_list is passed in array of db values where assigned-boolean = false
    random number between 1 and 9998 # i wouldn't use 0000 and 9999, may even want to remove all 1111, 2222, but will further reduce pool size
    if rand in db_list:
        db.assigned-boolean = true for rand
        return rand
    else:
        return new_pin(db_list)
上述问题;您可能有竞争条件,因此必须为db_列表锁定数据库表,其他调用必须等到db_列表可用,这样您就不会意外地分配两次pin(使用rand不太可能,但可能发生在具有小池的足够繁忙的站点上)

例如,另一个选择是增加url的复杂性 example.com/USER\u NAME/XXXX

并让用户选择XXXX并确保其具有唯一的名称。对于那些未注册的,您可以分配一个随机字

如果这太复杂;我建议允许代码长度从3到6,以便 example.com/pin/XXX example.con/pin/XXXX example.com/pin/XXXXX等


所有工作,如果引脚分配。这将大大增加您的池大小。

如果您有

class PinCode(models.Model):
    code = models.CharField(max_length='4', primary_key=True, validators=[lambda x: len(x) == 4])
    current_owner = models.ForeignKey(User, blank=True, null=True)
    created = models.DateTimeField(auto_now_add=True)

然后,要获得pin码,只需查询PinCodes,查找下一个未拥有或过期的pin码。

所需的只是
django extensions
包的
RandomCharField
。看

在代码中:

from django_extensions.db.fields import RandomCharField

class Inbox(models.Model):
    pin_code = RandomCharField(length=4, unique=True, include_alpha=False)
    owner = models.ForeignKey(User)
    creation_time = models.DateTimeField(auto_now_add=True)

关于记忆:是的,这是一项要求。问题是,我还在URL模式中使用生成的pin——因此为了避免冲突,它们必须是唯一的。但如果你是在暗示我让用户决定保留什么,保留多长时间——我的用户已经有了
昵称
,我可以使用。但许多是罕见的字符,有些是不适合长。如果你是复制粘贴的话,这也没问题,但是我实际上有一个相当大的人口,他们使用功能手机,而且实际上必须手动键入URL来共享它们(在我问题的可选部分阅读更多关于它的信息)。
from django_extensions.db.fields import RandomCharField

class Inbox(models.Model):
    pin_code = RandomCharField(length=4, unique=True, include_alpha=False)
    owner = models.ForeignKey(User)
    creation_time = models.DateTimeField(auto_now_add=True)