Django day005

Posted 12兵哥哥

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了Django day005相关的知识,希望对你有一定的参考价值。

ORM操作

  • 数据库数据类型:数字、字符串、时间、二进制,无布尔值

ORM分类

db first
	(1)先登录数据库,通过命令创建表结构及对应关系,
	(2)再通过工具连接上数据库,通过点操作,通过表结构生成类,不用写sql语句

code first(主流)
	通过类创建数据库,即转成sql数据,执行create
	(1)先写类
	(2)通过类,创建表结构
	例如:Django
  • 使用场景
    • 根据类自动创建数据库表
    • 根据类对数据库中的数据,进行各种操作

创建数据库表结构流程

  1. 写类

     app02中的models.py
     	# 创建的数据库表单名:app02_userinfo
     	class UserInfo(models.Model):
     	    # 默认创建ID列,自增, 主键
     	    # 用户名列,字符串类型,指定长度
     	    username = models.CharField(max_length=32)	#字符长度
     	    password = models.CharField(max_length=64)
    
  2. 注册app

     工程中的settings.py
     	INSTALLED_APPS中添加app命令,例如
     		INSTALLED_APPS = [
     		    \'django.contrib.admin\',
     		    \'django.contrib.auth\',
     		    \'django.contrib.contenttypes\',
     		    \'django.contrib.sessions\',
     		    \'django.contrib.messages\',
     		    \'django.contrib.staticfiles\',
     		    \'app02\',
     		]
    
  3. 根据情况配置使用数据库

     默认数据库(无需修改)
     DATABASES = {
         \'default\': {
             \'ENGINE\': \'django.db.backends.sqlite3\',
             \'NAME\': os.path.join(BASE_DIR, \'db.sqlite3\'),
         }
     }
    
     修改数据库方式,数据名(dbname)需要自己创建
     DATABASES = {
         \'default\': {
         \'ENGINE\': \'django.db.backends.mysql\',
         \'NAME\':\'dbname\',
         \'USER\': \'root\',
         \'PASSWORD\': \'xxx\',
         \'HOST\': \'\',
         \'PORT\': \'\',
         }
     }
    
     注:Django默认使用MySQLdb模块连接mysql数据库,但python 3.x中无该模块
     	需要改为pymysql:在project同名文件夹下的__init__.py文件中添加代码如下:
     		import pymysql
     		pymysql.install_as_MySQLdb()	
    
  4. 执行命令,生成表结构

    1. python manage.py makemigrations
    2. python manage.py migrate

基本操作

  •   方式一:
      models.UserInfo.objects.create(username=\'root\', password=\'123\')
    
      方式二:
      dict_user = {\'username\': \'Lucy\', \'password\': \'123\'}
      models.UserInfo.objects.create(**dict_user)
    
      方式三:
      obj = models.UserInfo(username=\'Tom\', password=\'123\')
      obj.save()
    
  •   models.UserInfo.objects.filter(username=\'Tom\').delete()
      models.UserInfo.objects.filter(id=1).delete()
      models.UserInfo.objects.all().delete()
    
  •   models.UserInfo.objects.all().update(password=999)
      models.UserInfo.objects.filter(id=7).update(password=666)
    
    • 单表

        select * from tb where id>1
        # 对应关系
        modles.tb.objects.filter(id__gt=1) #id>1
        modles.tb.objects.filter(id=1)
        modles.tb.objects.filter(id__lt=1)	# id<1
        modles.tb.objects.filter(id__gte=1) # id>=1
        modles.tb.objects.filter(id__lte=1)	# id<=1
      
        # result的类型是QuerySet,是Django提供的,类似列表
        # 全部
        result = models.UserInfo.objects.all()
        # 查看sql语句
        print(result.query)
        # 过滤全部满足条件的
        result = models.UserInfo.objects.filter(username=\'Tom\')	    
        for item in result:
            print(item.id, item.username, item.password)
      
        # 取第一个元素,没有为None
        obj1 = models.UserInfo.objects.filter(username="root", password="999").first()
        # 仅获取一条信息,但id不存在,会报错
        models.UserInfo.objects.get(id=nid)
        # 统计个数
        obj2 = models.UserInfo.objects.filter(username="root", password="999").count()
      
        # QuerySet类型,元素是对象
        v1 = models.Business.objects.all()
        # QuerySet类型,元素是字典
        v2 = models.Business.objects.all().values(\'id\', \'name\')
        # QuerySet类型,元素是元组
        v3 = models.Business.objects.all().values_list(\'id\', \'name\')
      
    • 跨表

      • 点操作

        • 应用场景:获取到QuerySet对象后的操作
      • 双下划线操作

        • 应用场景:在获取QuerSet对象前的操作,及写在models.Host.objects.xxx 上

        QuerySet类型,元素是对象,跨表通过点方式

        v1 = models.Host.objects.all() print(v1[0].nid, v1[0].port, v1[0].b_id, v1[0].b.name)

        QuerySet类型,元素是字典,跨表通过双下划线

        v2 = models.Host.objects.all().values(\'hostname\', \'b__name\') print(v2[0][\'hostname\'], v2[0][\'b__name\'])

        QuerySet类型,元素是元组

        v3 = models.Host.objects.all().values_list(\'nid\', \'hostname\', \'b_id\', \'b__name\') for row in v3: print(row[0], row[1], row[2], row[3])

操作表结构

  • 修改表结构

    (1)username = models.CharField(max_length=32) 修改为

    username = models.CharField(max_length=64)

    (2)再执行以下两条命令,重新生成表结构

    1. python manage.py makemigrations
    2. python manage.py migrate

    注:改小会存在数据丢失风险

  • 添加表结构

      方式一:	
      	(1)email = models.CharField(max_length=64)
      	(2)python manage.py makemigrations
      		选择1,输入默认值
      	(3)python manage.py migrate
      
      方式二:(指定默认为NULL)
      	(1)gender = models.CharField(max_length=64, null=True)
      	(2)python manage.py makemigrations
      	(3)python manage.py migrate
    
      方式三:(指定默认值)
      	(1)name_en = models.CharField(max_length=64, default=\'RDD\')
      	(2)python manage.py makemigrations
      	(3)python manage.py migrate
    
  • 删除表结构

      (1)# gender = models.CharField(max_length=64, null=True)
      (2)python manage.py makemigrations
      (3)python manage.py migrate
    

字段类型

  • 数据库常见类型:字符串、数字、时间、二进制

  • EmailField、URLField、GenericIPAddressField等类型

    • 本质:字符串
    • Django特有
    • 例如: email = models.EmailField(max_length=64)
    • 用途:Django后台管理时,使用,检测数据合法性
  • AutoField类型,用于自增

    • uid = models.AutoField(primary_key=True)

字段参阅

字段参数

null               -> db是否可以为空
default            -> 默认值
primary_key        -> 主键
db_column          -> 列名
db_index           -> 索引
unique			   -> 唯一索引
unique_for_date   	数据库中字段【日期】部分是否可以建立唯一索引
unique_for_month	数据库中字段【月】部分是否可以建立唯一索引
unique_for_year		数据库中字段【年】部分是否可以建立唯一索引
auto_now_add        -> 创建时,自动生成时间
	例如 
		app的views.py
			def login(request):
				models.UserGroup.objects.create(caption="monitor")

		app的models.py
			class UserGroup(models.Model):
			    uid = models.AutoField(primary_key=True)
			    caption = models.CharField(max_length=32)
			    ctime = models.DateTimeField(auto_now_add=True, null=True)
				uptime = models.DateTimeField(auto_now=True, null=True)


auto_now       -> 更新时,自动更新为当前时间
	例如:
		app的models.py
			uptime = models.DateTimeField(auto_now=True, null=True)

		app的views.py
			# 这种方式不支持
			obj = UserGroup.objects.filter(id=1).update(caption=\'CEO\') 

			# 这种方式:OK
			obj = models.UserGroup.objects.filter(uid=1).first()
			obj.caption = "CEO"
			obj.save()
	
choices			  -> django admin中显示下拉框,避免连表查询
	例如:
	app的models.py
		class UserInfo(models.Model):
		    # 默认创建ID列,自增, 主键
		    # 用户名列,字符串类型,指定长度
		    # 字符串、数字、时间、二进制
		    username = models.CharField(max_length=64)
		    password = models.CharField(max_length=64)
		    email = models.EmailField(max_length=64, null=True)
		    user_type_choices = (
		        (1, "超级用户"),
		        (2, "管理员"),
		        (3, "普通用户"),
		    )
		    user_type_id = models.IntegerField(choices=user_type_choices, default=3)

blank             -> django admin是否可以为空
verbose_name      -> django admin显示字段中文
editable          -> django admin是否可以被编辑
error_messages    -> 错误信息欠
help_text         -> django admin提示
validators		  -> django form ,自定义错误信息(欠)

参数参阅

以上是关于Django day005的主要内容,如果未能解决你的问题,请参考以下文章

领跑计划Day005Css

005day--linux基础一作业

Day 005:PAT练习--1047. 编程团体赛(20)

Django-C005-说说MVT之外的事情

如何在 Django Summernote 中显示编程片段的代码块?

apriori片段代码