Performance: leverage dict comprehension in PEP-0274

PEP-0274 introduced dict comprehensions to replace dict constructor
with a sequence of length-2 sequences, these are benefits copied
from [1]:
  The dictionary constructor approach has two distinct disadvantages
  from the proposed syntax though.  First, it isn't as legible as a
  dict comprehension.  Second, it forces the programmer to create an
  in-core list object first, which could be expensive.
Nova dropped python 2.6 support, we can leverage this now.
There is deep dive about PEP-0274[2] and basic tests about
performance[3].
Note: This commit doesn't handle dict constructor with kwagrs.
This commit also adds a hacking rule.

[1]http://legacy.python.org/dev/peps/pep-0274/
[2]http://doughellmann.com/2012/11/12/the-performance-impact-of-using-dict-instead-of-in-cpython-2-7-2.html
[3]http://paste.openstack.org/show/154798/

Change-Id: Ifb5cb05b9cc2b8758d5a8e34f7792470a73d7c40
This commit is contained in:
ChangBo Guo(gcb) 2014-12-24 18:10:30 +08:00
parent 27f157f67d
commit ab642b7d88
4 changed files with 15 additions and 14 deletions

View File

@ -47,6 +47,7 @@ Nova Specific Commandments
- [N334] Change assertTrue/False(A in/not in B, message) to the more specific
assertIn/NotIn(A, B, message)
- [N335] Check for usage of deprecated assertRaisesRegexp
- [N336] Must use a dict comprehension instead of a dict constructor with a sequence of key-value pairs.
Creating Unit Tests
-------------------

View File

@ -659,8 +659,8 @@ def compute_node_statistics(context):
fields = ('count', 'vcpus', 'memory_mb', 'local_gb', 'vcpus_used',
'memory_mb_used', 'local_gb_used', 'free_ram_mb', 'free_disk_gb',
'current_workload', 'running_vms', 'disk_available_least')
return dict((field, int(result[idx] or 0))
for idx, field in enumerate(fields))
return {field: int(result[idx] or 0)
for idx, field in enumerate(fields)}
###################
@ -3481,8 +3481,8 @@ def quota_reserve(context, resources, project_quotas, user_quotas, deltas,
usages = project_usages
else:
usages = user_usages
usages = dict((k, dict(in_use=v['in_use'], reserved=v['reserved']))
for k, v in usages.items())
usages = {k: dict(in_use=v['in_use'], reserved=v['reserved'])
for k, v in usages.items()}
LOG.debug('Raise OverQuota exception because: '
'project_quotas: %(project_quotas)s, '
'user_quotas: %(user_quotas)s, deltas: %(deltas)s, '
@ -4503,8 +4503,8 @@ def _dict_with_extra_specs(inst_type_query):
"""
inst_type_dict = dict(inst_type_query)
extra_specs = dict([(x['key'], x['value'])
for x in inst_type_query['extra_specs']])
extra_specs = {x['key']: x['value']
for x in inst_type_query['extra_specs']}
inst_type_dict['extra_specs'] = extra_specs
return inst_type_dict
@ -4711,7 +4711,7 @@ def _flavor_extra_specs_get_query(context, flavor_id, session=None):
@require_context
def flavor_extra_specs_get(context, flavor_id):
rows = _flavor_extra_specs_get_query(context, flavor_id).all()
return dict([(row['key'], row['value']) for row in rows])
return {row['key']: row['value'] for row in rows}
@require_context
@ -4835,7 +4835,7 @@ def _instance_metadata_get_query(context, instance_uuid, session=None):
@require_context
def instance_metadata_get(context, instance_uuid):
rows = _instance_metadata_get_query(context, instance_uuid).all()
return dict((row['key'], row['value']) for row in rows)
return {row['key']: row['value'] for row in rows}
@require_context
@ -4901,7 +4901,7 @@ def _instance_system_metadata_get_query(context, instance_uuid, session=None):
@require_context
def instance_system_metadata_get(context, instance_uuid):
rows = _instance_system_metadata_get_query(context, instance_uuid).all()
return dict((row['key'], row['value']) for row in rows)
return {row['key']: row['value'] for row in rows}
@require_context
@ -5417,7 +5417,7 @@ def aggregate_metadata_get(context, aggregate_id):
models.AggregateMetadata).\
filter_by(aggregate_id=aggregate_id).all()
return dict([(r['key'], r['value']) for r in rows])
return {r['key']: r['value'] for r in rows}
@require_aggregate_exists

View File

@ -60,8 +60,8 @@ def check_shadow_table(migrate_engine, table_name):
shadow_table = Table(db._SHADOW_TABLE_PREFIX + table_name, meta,
autoload=True)
columns = dict([(c.name, c) for c in table.columns])
shadow_columns = dict([(c.name, c) for c in shadow_table.columns])
columns = {c.name: c for c in table.columns}
shadow_columns = {c.name: c for c in shadow_table.columns}
for name, column in columns.iteritems():
if name not in shadow_columns:

View File

@ -41,8 +41,8 @@ class PolicyFixture(fixtures.Fixture):
def set_rules(self, rules):
policy = nova.policy._ENFORCER
policy.set_rules(dict((k, common_policy.parse_rule(v))
for k, v in rules.items()))
policy.set_rules({k: common_policy.parse_rule(v)
for k, v in rules.items()})
class RoleBasedPolicyFixture(fixtures.Fixture):