搜尋

Python-SQLALchemy

Feb 15, 2017 pm 03:25 PM
python

Initialization

# 检查是否已经安装以及版本号
>>> import sqlalchemy
>>> sqlalchemy.__version__ 
’1.1.4‘
>>> from sqlalchemy.ext.declarative import declarative_base
# model都是要继承自Base
>>> Base = declarative_base()

>>> from sqlalchemy import Column, Integer, String
>>> class User(Base):
...     __tablename__ = 'users' # 指定数据表名
...
...     id = Column(Integer, primary_key=True)
...     name = Column(String(50))
...     fullname = Column(String(50))
...     password = Column(String(50))
...
...     def __repr__(self):
...        return "<user>" % (
...                             self.name, self.fullname, self.password)


# 查看创建的数据表结构
>>> User.__table__ 
Table('users', MetaData(bind=None),
            Column('id', Integer(), table=<users>, primary_key=True, nullable=False),
            Column('name', String(length=50), table=<users>),
            Column('fullname', String(length=50), table=<users>),
            Column('password', String(length=50), table=<users>), schema=None)</users></users></users></users></user>

正式建立資料表

>>> from sqlalchemy import create_engine

# 连接到mysql
>>> engine = create_engine("mysql://root:root@localhost:3306/python?charset=utf8",
                           encoding="utf-8", echo=True)

# 正式创建数据表
>>> Base.metadata.create_all(engine)
CREATE TABLE users (
    id INTEGER NOT NULL AUTO_INCREMENT, 
    name VARCHAR(50), 
    fullname VARCHAR(50), 
    password VARCHAR(50), 
    PRIMARY KEY (id)
)

Creating a Session

下面的操作都是要透過會話物件操作

>>> from sqlalchemy.orm import sessionmaker
>>> Session = sessionmaker(bind=engine)
>>> session = Session()

Adding and Updating Objects

來過濾,

first

只列出第一個查詢到的對象

>>> ed_user = User(name='ed', fullname='Ed Jones', password='edspassword')
>>> session.add(ed_user)
使用add_all,一次性添加多個對象
>>> our_user = session.query(User).filter_by(name='ed').first()
BEGIN (implicit)
INSERT INTO users (name, fullname, password) VALUES (?, ?, ?)
('ed', 'Ed Jones', 'edspassword')

SELECT users.id AS users_id,
        users.name AS users_name,
        users.fullname AS users_fullname,
        users.password AS users_password
FROM users
WHERE users.name = ?
 LIMIT ? OFFSET ?
('ed', 1, 0)

>>> our_user
<user>

>>> ed_user is our_user
True</user>
Session很智能,比如說,它知道Ed Jones被修改了

>>> session.add_all([
...     User(name='wendy', fullname='Wendy Williams', password='foobar'),
...     User(name='mary', fullname='Mary Contrary', password='xxg527'),
...     User(name='fred', fullname='Fred Flinstone', password='blah')])
Session很智能,比如說,它知道Ed Jones被修改了
# 可以直接修改ed_user对象
>>> ed_user.password = 'f8s7ccs'

# session会自动知道哪些数据被修改了
>>> session.dirty
IdentitySet([<user>])

# session也可以知道哪些对象被新建了
>>> session.new
IdentitySet([<user>,
<user>,
<user>])</user></user></user></user>
Session很智能,比如說,它知道Ed Jones被修改了

>>> session.commit()
UPDATE users SET password=? WHERE users.id = ?
('f8s7ccs', 1)
INSERT INTO users (name, fullname, password) VALUES (?, ?, ?)
('wendy', 'Wendy Williams', 'foobar')
INSERT INTO users (name, fullname, password) VALUES (?, ?, ?)
('mary', 'Mary Contrary', 'xxg527')
INSERT INTO users (name, fullname, password) VALUES (?, ?, ?)
('fred', 'Fred Flinstone', 'blah')
COMMIT

>>> ed_user.id
BEGIN (implicit)
SELECT users.id AS users_id,
        users.name AS users_name,
        users.fullname AS users_fullname,
        users.password AS users_password
FROM users
WHERE users.id = ?
(1,)
1
Session很智能,比如說,它知道Ed Jones被修改了

>>> ed_user.name = 'Edwardo'
and we’ll add another erroneous user, fake_user:

>>> fake_user = User(name='fakeuser', fullname='Invalid', password='12345')
>>> session.add(fake_user)
Querying the session, we can see that they’re flushed into the current transaction:
Session很智能,比如說,它知道Ed Jones被修改了對資料庫進行了變更,自然要進行commit,從echo語句我們可以看出,我們更新了1個對象,創建了3個對象。

>>> session.query(User).filter(User.name.in_(['Edwardo', 'fakeuser'])).all()
UPDATE users SET name=? WHERE users.id = ?
('Edwardo', 1)
INSERT INTO users (name, fullname, password) VALUES (?, ?, ?)
('fakeuser', 'Invalid', '12345')
SELECT users.id AS users_id,
        users.name AS users_name,
        users.fullname AS users_fullname,
        users.password AS users_password
FROM users
WHERE users.name IN (?, ?)
('Edwardo', 'fakeuser')
[<user>, <user>]</user></user>

Rolling Back

因為Session是工作在一個transaction內部,有時候我們可能不小心做了一些誤刪除的操作,可以回滾。我們先修改ed_user的使用者名稱為Edwardo,然後重新新增一個User,但記住這個時候我們還沒有commit

>>> session.rollback()
ROLLBACK

>>> ed_user.name
BEGIN (implicit)
SELECT users.id AS users_id,
        users.name AS users_name,
        users.fullname AS users_fullname,
        users.password AS users_password
FROM users
WHERE users.id = ?
(1,)
u'ed'

>>> fake_user in session
False
issuing a SELECT illustrates the changes made to the database:
查詢檢驗一下

>>> session.query(User).filter(User.name.in_(['ed', 'fakeuser'])).all()
SELECT users.id AS users_id,
        users.name AS users_name,
        users.fullname AS users_fullname,
        users.password AS users_password
FROM users
WHERE users.name IN (?, ?)
('ed', 'fakeuser')
[<user>]</user>
回滾,我們可以知道ed_user's name is back to ed以及fake_user has been kicked out of the sessionuserdake,消失了,ed

用戶的名字重新變回了ed而不是Edwordo<pre class="brush:php;toolbar:false">&gt;&gt;&gt; session.query(User).filter(User.name.like('%ed')).count() 2 &gt;&gt;&gt; from sqlalchemy import func &gt;&gt;&gt; session.query(func.count(User.name), User.name).group_by(User.name).all() [(1, u'ed'), (1, u'fred'), (1, u'mary'), (1, u'wendy')]</pre>Couting

用於查詢操作相對應的count()

reee

reee

query

方法可以建立一個

Query object依照使用者id進行排序來進行查詢

>>> for instance in session.query(User).order_by(User.id):
...     print(instance.name, instance.fullname)
ed Ed Jones
wendy Wendy Williams
mary Mary Contrary
fred Fred Flinstone
query方法也可以接收ORM-instrumented descriptors作為參數。返回結果是一個named tuples

>>> for name, fullname in session.query(User.name, User.fullname):
...     print(name, fullname)
ed Ed Jones
wendy Wendy Williams
mary Mary Contrary
fred Fred Flinstone
The tuples returned by Query are named tuples, supplied by the KeyedTuple class, and can be treated much like an ordinary Python object. The names are the same as the attribute's name for an attribute, and the class name for a class:

>>> for row in session.query(User, User.name).all():
...    print(row.User, row.name)
<user> ed
<user> wendy
<user> mary
<user> fred</user></user></user></user>
You can control the names of inpidual column expressions using the

label()

construct, which is available from any ColumnElement-deriveive object, as d object class led object, sappd object, as d object tod d object, as class ob as User.name):

>>> for row in session.query(User.name.label('name_label')).all():
...    print(row.name_label)
ed
wendy
mary
fred
The name given to a full entity such as User, assuming that multiple entities are present in the call to query(), can be controlled using aliased)🎝 Query include issuing LIMIT and OFFSET, most conveniently using Python array slices and typically in conjunction with ORDER BY

:<pre class="brush:php;toolbar:false">&gt;&gt;&gt; from sqlalchemy.orm import aliased &gt;&gt;&gt; user_alias = aliased(User, name='user_alias') &gt;&gt;&gt; for row in session.query(user_alias, user_alias.name).all(): ...    print(row.user_alias) &lt;user&gt; &lt;user&gt; &lt;user&gt; &lt;user&gt;&lt;/user&gt;&lt;/user&gt;&lt;/user&gt;&lt;/user&gt;</pre>The Query object is fremully obects, moting thatry object is falkully 集, mi a​​llym be added . For example, to query for users named “ed” with a full name of “Ed Jones”, you can call

filter()

twice, which joins criteria using AND:

>>> for u in session.query(User).order_by(User.id)[1:3]:
...    print(u)
<user>
<user>
and filtering results, which is accomplished either with filter_by(), which uses keyword arguments:

>>> for name, in session.query(User.name).\
...             filter_by(fullname='Ed Jones'):
...    print(name)
ed

>>> for name, in session.query(User.name).\
...             filter(User.fullname=='Ed Jones'):
...    print(name)
ed</user></user>

filter )最常用的一些operators

>>> for user in session.query(User).\
...          filter(User.name=='ed').\
...          filter(User.fullname=='Ed Jones'):
...    print(user)
<user>
Common Filter Operators</user>
Building a Relationship創建物件與物件之間的關係,下面我們新建一個Address表,下面的操作相比django的orm繁瑣一些,要同時在兩個class內部同時設定relationship

equals:
query.filter(User.name == 'ed')

not equals:
query.filter(User.name != 'ed')

LIKE:
query.filter(User.name.like('%ed%'))

IN:
query.filter(User.name.in_(['ed', 'wendy', 'jack']))

# works with query objects too:
query.filter(User.name.in_(
        session.query(User.name).filter(User.name.like('%ed%'))
))

NOT IN:
query.filter(User.name.in_(['ed', 'wendy', 'jack']))

IS NULL:
query.filter(User.name == None)

# alternatively, if pep8/linters are a concern
query.filter(User.name.is_(None))

IS NOT NULL:
query.filter(User.name != None)

# alternatively, if pep8/linters are a concern
query.filter(User.name.isnot(None))

AND:
# use and_()
from sqlalchemy import and_
query.filter(and_(User.name == 'ed', User.fullname == 'Ed Jones'))

# or send multiple expressions to .filter()
query.filter(User.name == 'ed', User.fullname == 'Ed Jones')

# or chain multiple filter()/filter_by() calls
query.filter(User.name == 'ed').filter(User.fullname == 'Ed Jones')

Note
Make sure you use and_() and not the Python and operator!

OR:
from sqlalchemy import or_
query.filter(or_(User.name == 'ed', User.name == 'wendy'))

Note
Make sure you use or_() and not the Python or operator!

MATCH:
query.filter(User.name.match('wendy'))

Note
match() uses a database-specific MATCH or CONTAINS function;
its behavior will vary by backend and is not available on some backends such as SQLite.
Working with Related Objects現在我們創建了一個User,與它對應的一個空addresses集合也將創立。集合類型可以是各種合法類型,例如set/dictionaries(see Customizing Collection Access for details),但是預設集合是一個list。

現在我們再來建立一個使用者Jack

>>> from sqlalchemy import ForeignKey
>>> from sqlalchemy.orm import relationship

>>> class Address(Base):
...     __tablename__ = 'addresses'
...     id = Column(Integer, primary_key=True)
...     email_address = Column(String(50), nullable=False)
...     user_id = Column(Integer, ForeignKey('users.id'))
...
...     user = relationship("User", back_populates="addresses") # 将地址表和用户表关联
...
...     def __repr__(self):
...         return "<address>" % self.email_address


# 在用户表中还要重新设置一次
>>> User.addresses = relationship(
...     "Address", order_by=Address.id, back_populates="user")

>>> Base.metadata.create_all(engine)</address>
We are free to add Address objects on our User object. In this case we just assign a full list directly:

現在我們將使用者和一些地址關聯起來When using a bidirectional relationship, elements added in one direction automatically become visible in the other direction. This behavior occurs based on attribute on-change events and is evaluated in Python, without using 地址

>>> jack = User(name='jack', fullname='Jack Bean', password='gjffdd')
>>> jack.addresses
[]
Let's add and commit Jack Bean to the database. jack as well as the two Address members in the corresponding addresses collection are both added to the session at once, using aprocess collectionn both added to the session at once, using a processsnown 如何保存🜥到資料庫

>>> jack.addresses = [
...                 Address(email_address='jack@google.com'),
...                 Address(email_address='j25@yahoo.com')]
Querying for Jack, we get just Jack back. No SQL is yet issued for Jack's addresses:

>>> jack.addresses[1]
<address>

>>> jack.addresses[1].user
<user></user>
</address>
When we accessed the addresses collection, SQL was suddenly sload. addresses collection is now loaded and behaves just like an ordinary list. We'll cover ways to optimize the loading of this collection in a bit.

Delete


刪除操作,接下來我們嘗試刪除地址會因此刪除

>>> session.delete(jack)
>>> session.query(User).filter_by(name='jack').count()
0
So far, so good. How about Jack’s Address objects ?

>>> session.query(Address).filter(
...     Address.email_address.in_(['jack@google.com', 'j25@yahoo.com'])
...  ).count()
2

Uh oh, they’re still there ! Analyzing the flush SQL, we can see that the user_id column of each address was set to NULL, but the rows weren’t deleted. SQLAlchemy doesn’t assume that deletes cascade, you have to tell it to do so. Configuring delete/delete-orphan Cascade. We will configure cascade options on the User.addresses relationship to change the behavior. While SQLAlchemy allows you to add new attributes and relationships to mappings at any point in time, in this case the existing relationship needs to be removed, so we need to tear down the mappings completely and start again - we’ll close the Session:

直接close来rollback,并不进行commit

>>> session.close()
ROLLBACK

Use a new declarative_base():

>>> Base = declarative_base()

Next we’ll declare the User class, adding in the addresses relationship
including the cascade configuration (we’ll leave the constructor out too):

>>> class User(Base):
...     __tablename__ = 'users'
...
...     id = Column(Integer, primary_key=True)
...     name = Column(String(50))
...     fullname = Column(String(50))
...     password = Column(String(50))
...
...     addresses = relationship("Address", back_populates='user',
...                     cascade="all, delete, delete-orphan")
...
...     def __repr__(self):
...        return "<user>" % (
...                                self.name, self.fullname, self.password)</user>

Then we recreate Address, noting that in this case
we’ve created the Address.user relationship via the User class already:

>>> class Address(Base):
...     __tablename__ = 'addresses'
...     id = Column(Integer, primary_key=True)
...     email_address = Column(String(50), nullable=False)
...     user_id = Column(Integer, ForeignKey('users.id'))
...     user = relationship("User", back_populates="addresses")
...
...     def __repr__(self):
...         return "<address>" % self.email_address</address>

Now when we load the user jack (below using get(), which loads by primary key), removing an address from the corresponding addresses collection will result in that Address being deleted:

# load Jack by primary key
>>> jack = session.query(User).get(5)

# remove one Address (lazy load fires off)
>>> del jack.addresses[1]

# only one address remains
>>> session.query(Address).filter(
...     Address.email_address.in_(['jack@google.com', 'j25@yahoo.com'])
... ).count()
1

Deleting Jack will delete both Jack and the remaining Address associated with the user:

>>> session.delete(jack)

>>> session.query(User).filter_by(name='jack').count()
0

>>> session.query(Address).filter(
...    Address.email_address.in_(['jack@google.com', 'j25@yahoo.com'])
... ).count()
0

Further detail on configuration of cascades is at Cascades. The cascade functionality can also integrate smoothly with the ON DELETE CASCADE functionality of the relational database. See Using Passive Deletes for details.

backref

上面同时设置两个relationship太麻烦了,可以使用backref

from sqlalchemy import Integer, ForeignKey, String, Column
from sqlalchemy.ext.declarative import declarative_base
from sqlalchemy.orm import relationship

Base = declarative_base()

class User(Base):
    __tablename__ = 'user'
    id = Column(Integer, primary_key=True)
    name = Column(String)

    addresses = relationship("Address", backref="user")

class Address(Base):
    __tablename__ = 'address'
    id = Column(Integer, primary_key=True)
    email = Column(String)
    user_id = Column(Integer, ForeignKey('user.id'))

The above configuration establishes a collection of Address objects on User called User.addresses. It also establishes a .user attribute on Address which will refer to the parent User object.

In fact, the backref keyword is only a common shortcut for placing a second relationship() onto the Address mapping, including the establishment of an event listener on both sides which will mirror attribute operations in both directions. The above configuration is equivalent to:

rom sqlalchemy import Integer, ForeignKey, String, Column
from sqlalchemy.ext.declarative import declarative_base
from sqlalchemy.orm import relationship

Base = declarative_base()

class User(Base):
    __tablename__ = 'user'
    id = Column(Integer, primary_key=True)
    name = Column(String)

    addresses = relationship("Address", back_populates="user")
        
class Address(Base):
    __tablename__ = 'address'
    id = Column(Integer, primary_key=True)
    email = Column(String)
    user_id = Column(Integer, ForeignKey('user.id'))

    user = relationship("User", back_populates="addresses")

Above, we add a .user relationship to Address explicitly. On both relationships, the back_populates directive tells each relationship about the other one, indicating that they should establish “bidirectional” behavior between each other. The primary effect of this configuration is that the relationship adds event handlers to both attributes which have the behavior of “when an append or set event occurs here, set ourselves onto the incoming attribute using this particular attribute name”. The behavior is illustrated as follows. Start with a User and an Address instance. The .addresses collection is empty, and the .user attribute is None:

>>> u1 = User()
>>> a1 = Address()
>>> u1.addresses
[]
>>> print(a1.user)
None

However, once the Address is appended to the u1.addresses collection, both the collection and the scalar attribute have been populated:

>>> u1.addresses.append(a1)
>>> u1.addresses
[<__main__.address>]
>>> a1.user
<__main__.user></__main__.user></__main__.address>

This behavior of course works in reverse for removal operations as well, as well as for equivalent operations on both sides. Such as when .user is set again to None, the Address object is removed from the reverse collection:

>>> a1.user = None
>>> u1.addresses
[]

The manipulation of the .addresses collection and the .user attribute occurs entirely in Python without any interaction with the SQL database. Without this behavior, the proper state would be apparent on both sides once the data has been flushed to the database, and later reloaded after a commit or expiration operation occurs. The backref/back_populates behavior has the advantage that common bidirectional operations can reflect the correct state without requiring a database round trip.

Remember, when the backref keyword is used on a single relationship, it’s exactly the same as if the above two relationships were created inpidually using back_populates on each.

mysql操作

检验一下我们上面的成果以及熟悉创建的mysql表的结构

地址表的结构

> SHOW CREATE TABLE addresses;
+-----------+----------------+
| Table     | Create Table   |
|-----------+----------------|
| addresses | CREATE TABLE `addresses` (
  `id` int(11) NOT NULL AUTO_INCREMENT,
  `email_address` varchar(50) NOT NULL,
  `user_id` int(11) DEFAULT NULL,
  PRIMARY KEY (`id`),
  KEY `user_id` (`user_id`),
  CONSTRAINT `addresses_ibfk_1` FOREIGN KEY (`user_id`) REFERENCES `users` (`id`)
) ENGINE=InnoDB AUTO_INCREMENT=5 DEFAULT CHARSET=utf8                |
+-----------+----------------+
1 row in set
Time: 0.005s

> DESC addresses;
+---------------+-------------+--------+-------+-----------+----------------+
| Field         | Type        | Null   | Key   |   Default | Extra          |
|---------------+-------------+--------+-------+-----------+----------------|
| id            | int(11)     | NO     | PRI   |    <null> | auto_increment |
| email_address | varchar(50) | NO     |       |    <null> |                |
| user_id       | int(11)     | YES    | MUL   |    <null> |                |
+---------------+-------------+--------+-------+-----------+----------------+
3 rows in set
Time: 0.002s</null></null></null>

用户表的结构

> SHOW CREATE TABLE users;
+---------+----------------+
| Table   | Create Table   |
|---------+----------------|
| users   | CREATE TABLE `users` (
  `id` int(11) NOT NULL AUTO_INCREMENT,
  `name` varchar(50) DEFAULT NULL,
  `fullname` varchar(50) DEFAULT NULL,
  `password` varchar(50) DEFAULT NULL,
  PRIMARY KEY (`id`)
) ENGINE=InnoDB AUTO_INCREMENT=6 DEFAULT CHARSET=utf8                |
+---------+----------------+
1 row in set
Time: 0.002s

> DESC users;
+----------+-------------+--------+-------+-----------+----------------+
| Field    | Type        | Null   | Key   |   Default | Extra          |
|----------+-------------+--------+-------+-----------+----------------|
| id       | int(11)     | NO     | PRI   |    <null> | auto_increment |
| name     | varchar(50) | YES    |       |    <null> |                |
| fullname | varchar(50) | YES    |       |    <null> |                |
| password | varchar(50) | YES    |       |    <null> |                |
+----------+-------------+--------+-------+-----------+----------------+
4 rows in set
Time: 0.003s</null></null></null></null>

详细数据

> SELECT * FROM addresses;
+------+-----------------+-----------+
|   id | email_address   |   user_id |
|------+-----------------+-----------|
|    3 | jack@google.com |         5 |
|    4 | j25@yahoo.com   |         5 |
+------+-----------------+-----------+
2 rows in set
Time: 0.002s

> SELECT * FROM users;
+------+--------+----------------+------------+
|   id | name   | fullname       | password   |
|------+--------+----------------+------------|
|    1 | ed     | Ed Jones       | f8s7ccs    |
|    2 | wendy  | Wendy Williams | foobar     |
|    3 | mary   | Mary Contrary  | xxg527     |
|    4 | fred   | Fred Flinstone | blah       |
|    5 | jack   | Jack Bean      | gjffdd     |
+------+--------+----------------+------------+
5 rows in set
Time: 0.003s

知乎live设计模型

from sqlalchemy import Column, String, Integer, create_engine, SmallInteger
from sqlalchemy.orm import sessionmaker
from sqlalchemy.ext.declarative import declarative_base

DB_URI = 'sqlite:///user.db'
Base = declarative_base()
engine = create_engine(DB_URI)
Base.metadata.bind = engine
Session = sessionmaker(bind=engine)
session = Session()
class User(Base):
    __tablename__ = 'live_user'
    
    id = Column(Integer, unique=True, primary_key=True, autoincrement=True)
    speaker_id = Column(String(40), index=True, unique=True)
    name = Column(String(40), index=True, nullable=False)
    gender = Column(SmallInteger, default=2)
    headline = Column(String(200))
    avatar_url = Column(String(100), nullable=False)
    bio = Column(String(200))
    description = Column(String())
    
    @classmethod
    def add(cls, **kwargs):
        speaker_id = kwargs.get('speaker_id', None)
        if id is not None:
            r = session.query(cls).filter_by(speaker_id=speaker_id).first()
            if r:
                return r
        try:
            r = cls(**kwargs)
            session.add(r)
            session.commit()
        except:
            session.rollback()
            raise
        else:
            return r
Base.metadata.create_all()

接口分为2种:

  1. http://www.php.cn/ (未结束)

  2. http://www.php.cn/ (已结束)

elasticsearch-dsl-py相比elasticsearch-py做了各种封装,DSL也支持用类代表一个doc_type(类似数据库中的Table),实现ORM的效果。我们就用它来写Live模型:

from elasticsearch_dsl import DocType, Date, Integer, Text, Float, Boolean
from elasticsearch_dsl.connections import connections
from elasticsearch_dsl.query import SF, Q
from config import SEARCH_FIELDS
from .speaker import User, session

connections.create_connection(hosts=['localhost'])
class Live(DocType):
    id = Integer()
    speaker_id = Integer()
    feedback_score = Float() # 评分
    topic_names = Text(analyzer='ik_max_word')  # 话题标签名字
    seats_taken = Integer()  # 参与人数
    subject = Text(analyzer='ik_max_word')  # 标题
    amount = Float()  # 价格(RMB)
    description = Text(analyzer='ik_max_word')
    status = Boolean()  # public(True)/ended(False)
    starts_at = Date()
    outline = Text(analyzer='ik_max_word')  # Live内容
    speaker_message_count = Integer()
    tag_names = Text(analyzer='ik_max_word')
    liked_num = Integer()
    
    class Meta:
        index = 'live'
        
    @classmethod
    def add(cls, **kwargs):
        id = kwargs.pop('id', None)
        if id is None:
            return False
        live = cls(meta={'id': id}, **kwargs)
        live.save()
        return live

它允许我们用一种非常可维护的方法来组织字典:

In : from elasticsearch_dsl.query import Q
In : Q('multi_match', subject='python').to_dict()
Out: {'multi_match': {'subject': 'python'}}
In : from elasticsearch import Elasticsearch
In : from elasticsearch_dsl import Search, Q
In : s = Search(using=client, index='live')
In : s = s.query('match', subject='python').query(~Q('match', description='量化'))
In : s.execute()
Out: <response:>]></response:>

上述例子表示从live这个索引(类似数据库中的Database)中找到subject字典包含python,但是description字段不包含量化的Live。

更多Python-SQLALchemy 相关文章请关注PHP中文网!


陳述
本文內容由網友自願投稿,版權歸原作者所有。本站不承擔相應的法律責任。如發現涉嫌抄襲或侵權的內容,請聯絡admin@php.cn
Python和時間:充分利用您的學習時間Python和時間:充分利用您的學習時間Apr 14, 2025 am 12:02 AM

要在有限的時間內最大化學習Python的效率,可以使用Python的datetime、time和schedule模塊。 1.datetime模塊用於記錄和規劃學習時間。 2.time模塊幫助設置學習和休息時間。 3.schedule模塊自動化安排每週學習任務。

Python:遊戲,Guis等Python:遊戲,Guis等Apr 13, 2025 am 12:14 AM

Python在遊戲和GUI開發中表現出色。 1)遊戲開發使用Pygame,提供繪圖、音頻等功能,適合創建2D遊戲。 2)GUI開發可選擇Tkinter或PyQt,Tkinter簡單易用,PyQt功能豐富,適合專業開發。

Python vs.C:申請和用例Python vs.C:申請和用例Apr 12, 2025 am 12:01 AM

Python适合数据科学、Web开发和自动化任务,而C 适用于系统编程、游戏开发和嵌入式系统。Python以简洁和强大的生态系统著称,C 则以高性能和底层控制能力闻名。

2小時的Python計劃:一種現實的方法2小時的Python計劃:一種現實的方法Apr 11, 2025 am 12:04 AM

2小時內可以學會Python的基本編程概念和技能。 1.學習變量和數據類型,2.掌握控制流(條件語句和循環),3.理解函數的定義和使用,4.通過簡單示例和代碼片段快速上手Python編程。

Python:探索其主要應用程序Python:探索其主要應用程序Apr 10, 2025 am 09:41 AM

Python在web開發、數據科學、機器學習、自動化和腳本編寫等領域有廣泛應用。 1)在web開發中,Django和Flask框架簡化了開發過程。 2)數據科學和機器學習領域,NumPy、Pandas、Scikit-learn和TensorFlow庫提供了強大支持。 3)自動化和腳本編寫方面,Python適用於自動化測試和系統管理等任務。

您可以在2小時內學到多少python?您可以在2小時內學到多少python?Apr 09, 2025 pm 04:33 PM

兩小時內可以學到Python的基礎知識。 1.學習變量和數據類型,2.掌握控制結構如if語句和循環,3.了解函數的定義和使用。這些將幫助你開始編寫簡單的Python程序。

如何在10小時內通過項目和問題驅動的方式教計算機小白編程基礎?如何在10小時內通過項目和問題驅動的方式教計算機小白編程基礎?Apr 02, 2025 am 07:18 AM

如何在10小時內教計算機小白編程基礎?如果你只有10個小時來教計算機小白一些編程知識,你會選擇教些什麼�...

如何在使用 Fiddler Everywhere 進行中間人讀取時避免被瀏覽器檢測到?如何在使用 Fiddler Everywhere 進行中間人讀取時避免被瀏覽器檢測到?Apr 02, 2025 am 07:15 AM

使用FiddlerEverywhere進行中間人讀取時如何避免被檢測到當你使用FiddlerEverywhere...

See all articles

熱AI工具

Undresser.AI Undress

Undresser.AI Undress

人工智慧驅動的應用程序,用於創建逼真的裸體照片

AI Clothes Remover

AI Clothes Remover

用於從照片中去除衣服的線上人工智慧工具。

Undress AI Tool

Undress AI Tool

免費脫衣圖片

Clothoff.io

Clothoff.io

AI脫衣器

AI Hentai Generator

AI Hentai Generator

免費產生 AI 無盡。

熱門文章

R.E.P.O.能量晶體解釋及其做什麼(黃色晶體)
4 週前By尊渡假赌尊渡假赌尊渡假赌
R.E.P.O.最佳圖形設置
4 週前By尊渡假赌尊渡假赌尊渡假赌
R.E.P.O.如果您聽不到任何人,如何修復音頻
4 週前By尊渡假赌尊渡假赌尊渡假赌
WWE 2K25:如何解鎖Myrise中的所有內容
1 個月前By尊渡假赌尊渡假赌尊渡假赌

熱工具

SAP NetWeaver Server Adapter for Eclipse

SAP NetWeaver Server Adapter for Eclipse

將Eclipse與SAP NetWeaver應用伺服器整合。

SublimeText3 Mac版

SublimeText3 Mac版

神級程式碼編輯軟體(SublimeText3)

Atom編輯器mac版下載

Atom編輯器mac版下載

最受歡迎的的開源編輯器

Dreamweaver CS6

Dreamweaver CS6

視覺化網頁開發工具

EditPlus 中文破解版

EditPlus 中文破解版

體積小,語法高亮,不支援程式碼提示功能