[机器学习速成课程] 稀疏性正则化 (Regularization for Sparsity)-学习笔记

article/2025/10/26 7:12:09

稀疏性和 L1 正则化

学习目标:

  • 计算模型大小
  • 通过应用 L1 正则化来增加稀疏性,以减小模型大小

降低复杂性的一种方法是使用正则化函数,它会使权重正好为零。对于线性模型(例如线性回归),权重为零就相当于完全没有使用相应特征。除了可避免过拟合之外,生成的模型还会更加有效。

L1 正则化是一种增加稀疏性的好方法。

导入,跟之前一样

import mathfrom IPython import display
from matplotlib import cm
from matplotlib import gridspec
from matplotlib import pyplot as plt
import numpy as np
import pandas as pd
from sklearn import metrics
import tensorflow as tf
from tensorflow.python.data import Datasettf.logging.set_verbosity(tf.logging.ERROR)
pd.options.display.max_rows = 10
pd.options.display.float_format = '{:.1f}'.formatcalifornia_housing_dataframe = pd.read_csv("https://storage.googleapis.com/mledu-datasets/california_housing_train.csv", sep=",")california_housing_dataframe = california_housing_dataframe.reindex(np.random.permutation(california_housing_dataframe.index))

样本特征,跟之前一样

def preprocess_features(california_housing_dataframe):"""Prepares input features from California housing data set.Args:california_housing_dataframe: A Pandas DataFrame expected to contain datafrom the California housing data set.Returns:A DataFrame that contains the features to be used for the model, includingsynthetic features."""selected_features = california_housing_dataframe[["latitude","longitude","housing_median_age","total_rooms","total_bedrooms","population","households","median_income"]]processed_features = selected_features.copy()# Create a synthetic feature.processed_features["rooms_per_person"] = (california_housing_dataframe["total_rooms"] /california_housing_dataframe["population"])return processed_featuresdef preprocess_targets(california_housing_dataframe):"""Prepares target features (i.e., labels) from California housing data set.Args:california_housing_dataframe: A Pandas DataFrame expected to contain datafrom the California housing data set.Returns:A DataFrame that contains the target feature."""output_targets = pd.DataFrame()# Create a boolean categorical feature representing whether the# medianHouseValue is above a set threshold.output_targets["median_house_value_is_high"] = (california_housing_dataframe["median_house_value"] > 265000).astype(float)return output_targets

样本集和验证集,与之前一样

# Choose the first 12000 (out of 17000) examples for training.
training_examples = preprocess_features(california_housing_dataframe.head(12000))
training_targets = preprocess_targets(california_housing_dataframe.head(12000))# Choose the last 5000 (out of 17000) examples for validation.
validation_examples = preprocess_features(california_housing_dataframe.tail(5000))
validation_targets = preprocess_targets(california_housing_dataframe.tail(5000))# Double-check that we've done the right thing.
print "Training examples summary:"
display.display(training_examples.describe())
print "Validation examples summary:"
display.display(validation_examples.describe())print "Training targets summary:"
display.display(training_targets.describe())
print "Validation targets summary:"
display.display(validation_targets.describe())

输入函数,与之前一样

def my_input_fn(features, targets, batch_size=1, shuffle=True, num_epochs=None):"""Trains a linear regression model of one feature.Args:features: pandas DataFrame of featurestargets: pandas DataFrame of targetsbatch_size: Size of batches to be passed to the modelshuffle: True or False. Whether to shuffle the data.num_epochs: Number of epochs for which data should be repeated. None = repeat indefinitelyReturns:Tuple of (features, labels) for next data batch"""# Convert pandas data into a dict of np arrays.features = {key:np.array(value) for key,value in dict(features).items()}                                            # Construct a dataset, and configure batching/repeatingds = Dataset.from_tensor_slices((features,targets)) # warning: 2GB limitds = ds.batch(batch_size).repeat(num_epochs)# Shuffle the data, if specifiedif shuffle:ds = ds.shuffle(10000)# Return the next batch of datafeatures, labels = ds.make_one_shot_iterator().get_next()return features, labels

分桶函数

# get_quantile_based_boundaries 会根据num_buckets(指定的分桶数量),来对feature_values进行分桶。
def get_quantile_based_buckets(feature_values, num_buckets):quantiles = feature_values.quantile([(i+1.)/(num_buckets + 1.) for i in xrange(num_buckets)])return [quantiles[q] for q in quantiles.keys()]

对样本对特征进行分桶

def construct_feature_columns():"""Construct the TensorFlow Feature Columns.Returns:A set of feature columns"""bucketized_households = tf.feature_column.bucketized_column(tf.feature_column.numeric_column("households"),boundaries=get_quantile_based_buckets(training_examples["households"], 10))bucketized_longitude = tf.feature_column.bucketized_column(tf.feature_column.numeric_column("longitude"),boundaries=get_quantile_based_buckets(training_examples["longitude"], 50))bucketized_latitude = tf.feature_column.bucketized_column(tf.feature_column.numeric_column("latitude"),boundaries=get_quantile_based_buckets(training_examples["latitude"], 50))bucketized_housing_median_age = tf.feature_column.bucketized_column(tf.feature_column.numeric_column("housing_median_age"),boundaries=get_quantile_based_buckets(training_examples["housing_median_age"], 10))bucketized_total_rooms = tf.feature_column.bucketized_column(tf.feature_column.numeric_column("total_rooms"),boundaries=get_quantile_based_buckets(training_examples["total_rooms"], 10))bucketized_total_bedrooms = tf.feature_column.bucketized_column(tf.feature_column.numeric_column("total_bedrooms"),boundaries=get_quantile_based_buckets(training_examples["total_bedrooms"], 10))bucketized_population = tf.feature_column.bucketized_column(tf.feature_column.numeric_column("population"),boundaries=get_quantile_based_buckets(training_examples["population"], 10))bucketized_median_income = tf.feature_column.bucketized_column(tf.feature_column.numeric_column("median_income"),boundaries=get_quantile_based_buckets(training_examples["median_income"], 10))bucketized_rooms_per_person = tf.feature_column.bucketized_column(tf.feature_column.numeric_column("rooms_per_person"),boundaries=get_quantile_based_buckets(training_examples["rooms_per_person"], 10))# 添加 longitude 与 latitude 的特征组合  # hash_bucket_size 参数指定 hash bucket 的桶个数,特征交叉的组合个数越多,hash_bucket_size 也应相应增加,从而减小哈希冲突  long_x_lat = tf.feature_column.crossed_column(set([bucketized_longitude, bucketized_latitude]), hash_bucket_size=1000)feature_columns = set([long_x_lat,bucketized_longitude,bucketized_latitude,bucketized_housing_median_age,bucketized_total_rooms,bucketized_total_bedrooms,bucketized_population,bucketized_households,bucketized_median_income,bucketized_rooms_per_person])return feature_columns

计算模型大小

要计算模型大小,只需计算非零参数的数量即可。为此,我们在下面提供了一个辅助函数。该函数深入使用了 Estimator API,如果不了解它的工作原理,也不用担心。

def model_size(estimator):# 取得所有变量对名称variables = estimator.get_variable_names()size = 0# 遍历所有变量名for variable in variables:# 如果变量名中不存在'global_step','centered_bias_weight','bias_weight','Ftrl'字串,# 就累加一个非零参数# 为什么可以这样判断? 这些字串代表什么?if not any(x in variable for x in ['global_step','centered_bias_weight','bias_weight','Ftrl']):# 累加一个非零参数size += np.count_nonzero(estimator.get_variable_value(variable))return size

减小模型大小

您的团队需要针对 SmartRing 构建一个准确度高的逻辑回归模型,这种指环非常智能,可以感应城市街区的人口统计特征(median_incomeavg_roomshouseholds 等等),并告诉您指定城市街区的住房成本是否高昂。

由于 SmartRing 很小,因此工程团队已确定它只能处理参数数量不超过 600 个的模型。另一方面,产品管理团队也已确定,除非所保留测试集的对数损失函数低于 0.35,否则该模型不能发布。

您可以使用秘密武器“L1 正则化”调整模型,使其同时满足大小和准确率限制条件吗?

任务 1:查找合适的正则化系数。

查找可同时满足以下两种限制条件的 L1 正则化强度参数:模型的参数数量不超过 600 个验证集的对数损失函数低于 0.35

以下代码可帮助您快速开始。您可以通过多种方法向您的模型应用正则化。在此练习中,我们选择使用 FtrlOptimizer 来应用正则化。FtrlOptimizer 是一种设计成使用 L1 正则化比标准梯度下降法得到更好结果的方法。

重申一次,我们会使用整个数据集来训练该模型,因此预计其运行速度会比通常要慢。

线性分类模型
def train_linear_classifier_model(learning_rate,regularization_strength,steps,batch_size,feature_columns,training_examples,training_targets,validation_examples,validation_targets):"""Trains a linear regression model.In addition to training, this function also prints training progress information,as well as a plot of the training and validation loss over time.Args:learning_rate: A `float`, the learning rate.regularization_strength: A `float` that indicates the strength of the L1regularization. A value of `0.0` means no regularization.steps: A non-zero `int`, the total number of training steps. A training stepconsists of a forward and backward pass using a single batch.feature_columns: A `set` specifying the input feature columns to use.training_examples: A `DataFrame` containing one or more columns from`california_housing_dataframe` to use as input features for training.training_targets: A `DataFrame` containing exactly one column from`california_housing_dataframe` to use as target for training.validation_examples: A `DataFrame` containing one or more columns from`california_housing_dataframe` to use as input features for validation.validation_targets: A `DataFrame` containing exactly one column from`california_housing_dataframe` to use as target for validation.Returns:A `LinearClassifier` object trained on the training data."""periods = 7steps_per_period = steps / periods# Create a linear classifier object.# FtrlOptimizer 是一种设计成使用 L1 正则化比标准梯度下降法得到更好结果的方法。my_optimizer = tf.train.FtrlOptimizer(learning_rate=learning_rate, l1_regularization_strength=regularization_strength)my_optimizer = tf.contrib.estimator.clip_gradients_by_norm(my_optimizer, 5.0)# linear_classifier = tf.estimator.LinearClassifier线性分类  linear_classifier = tf.estimator.LinearClassifier(feature_columns=feature_columns,optimizer=my_optimizer)# Create input functions.training_input_fn = lambda: my_input_fn(training_examples, training_targets["median_house_value_is_high"], batch_size=batch_size)predict_training_input_fn = lambda: my_input_fn(training_examples, training_targets["median_house_value_is_high"], num_epochs=1, shuffle=False)predict_validation_input_fn = lambda: my_input_fn(validation_examples, validation_targets["median_house_value_is_high"], num_epochs=1, shuffle=False)# Train the model, but do so inside a loop so that we can periodically assess# loss metrics.print "Training model..."print "LogLoss (on validation data):"training_log_losses = []validation_log_losses = []for period in range (0, periods):# Train the model, starting from the prior state.linear_classifier.train(input_fn=training_input_fn,steps=steps_per_period)# Take a break and compute predictions.training_probabilities = linear_classifier.predict(input_fn=predict_training_input_fn)training_probabilities = np.array([item['probabilities'] for item in training_probabilities])validation_probabilities = linear_classifier.predict(input_fn=predict_validation_input_fn)validation_probabilities = np.array([item['probabilities'] for item in validation_probabilities])# Compute training and validation loss.training_log_loss = metrics.log_loss(training_targets, training_probabilities)validation_log_loss = metrics.log_loss(validation_targets, validation_probabilities)# Occasionally print the current loss.print "  period %02d : %0.2f" % (period, validation_log_loss)# Add the loss metrics from this period to our list.training_log_losses.append(training_log_loss)validation_log_losses.append(validation_log_loss)print "Model training finished."# Output a graph of loss metrics over periods.plt.ylabel("LogLoss")plt.xlabel("Periods")plt.title("LogLoss vs. Periods")plt.tight_layout()plt.plot(training_log_losses, label="training")plt.plot(validation_log_losses, label="validation")plt.legend()return linear_classifier

默认L1 正则化强度参数为0.0时

linear_classifier = train_linear_classifier_model(learning_rate=0.1,# TWEAK THE REGULARIZATION VALUE BELOW# 默认L1 正则化强度参数为0.0时regularization_strength=0.0, steps=300,batch_size=100,feature_columns=construct_feature_columns(),training_examples=training_examples,training_targets=training_targets,validation_examples=validation_examples,validation_targets=validation_targets)
print "Model size:", model_size(linear_classifier)


修改L1 正则化强度参数为0.1时


修改L1 正则化强度参数为0.5时


修改L1 正则化强度参数为1.0时



http://chatgpt.dhexx.cn/article/LCutWm9o.shtml

相关文章

机器学习14:稀疏性-Sparsity

现实世界中,问题的特征的数量往往是很大的,而其中起决定性作用的往往是很小的一部分,稀疏规则化算子的引入会学习去掉这些没有信息的特征,也就是把这些特征对应的权重置为 0。 1.稀疏性正则化:L₁ 正则化 稀疏向量通常…

稀疏(sparsity)矩阵的行压缩存储

压缩矩阵行或列来存储矩阵的格式是很普遍的,它们不会存储不必要的元素(即空值)。但是它们也不是非常有效的,当在一个矩阵-向量积或预解决的每个简单标量中需要间接寻址。行压缩存储方式会把一个稀疏矩阵行的非零数值放在连续的存储…

redis删除锁

redis删除锁 参考:百度安全验证 前言 在分布式系统中,由于redis分布式锁相对于更简单和高效,成为了分布式锁的首先,被我们用到了很多实际业务场景当中。 但不是说用了redis分布式锁,就可以高枕无忧了,如…

Redis进阶: 锁的使用

Redis进阶: 锁的使用 1. 概念1. 原子性2. 事务 2. 使用Redis构建全局并发锁3. Redlock(redis分布式锁)总结 相关Blog 1. 概念 1. 原子性 原子性 原子性是数据库的事务中的特性。在数据库事务的情景下,原子性指的是:一个事务&…

redis锁的几种实现

1. redis加锁分类 redis能用的的加锁命令分表是INCR、SETNX、SET 2. 第一种锁命令INCR 这种加锁的思路是, key 不存在,那么 key 的值会先被初始化为 0 ,然后再执行 INCR 操作进行加一。 然后其它用户在执行 INCR 操作进行加一时&#xff0…

java redis锁_Java中Redis锁的实现

由于具体业务场景的需求,需要保证数据在分布式环境下的正确更新,所以研究了一下Java中分布式锁的实现。 Java分布式锁的实现方式主要有以下三种: 数据库实现的乐观锁 Redis实现的分布式锁 Zookeeper实现的分布式锁 其中,较常用的是前两种方式,但是数据库实现方式需要较多的…

Redis的分布式锁详解

一、什么是分布式锁: 1、什么是分布式锁: 分布式锁,即分布式系统中的锁。在单体应用中我们通过锁解决的是控制共享资源访问的问题,而分布式锁,就是解决了分布式系统中控制共享资源访问的问题。与单体应用不同的是&…

redis锁

一、redis锁的实现 加锁命令: SETNX key value: 当键不存在时,对键进行设置操作并返回成功1,否则返回失败0。 Key是锁的唯一标识,一般按业务来决定命名; Value 往往用来比较加锁的是哪一个线程或者哪一个…

超图 hypergraph 二分图 Bipartite graph

超图是什么 超图超图的意义应用 二分图 超图 超图是什么? 超图的本质特征在于它的超边,它可以连接两个以上的结点(包括两个)。按这样的意义来说,我们所熟悉的普通图只是超图的一个特例而已,而超图则定义了一个更加宽泛的图。 超图…

BiNE: Bipartite Network Embedding 阅读笔记

论文传送门 作者 华东师范大学: 高明周傲英Leihui Chen 中国科学技术大学:何向南 摘要 传统的学习图数据的节点表示的方法大都聚焦于一般的同构网络,忽略了二部图的特殊性质。因此这些方法对于二部图嵌入来说可能是次优的。 本文提出了B…

C#,图论与图算法,二分图(Bipartite Graph)最佳二分匹配(Maximum Bipartite Matching)算法与源程序

二部图中的匹配是一组边的选择方式,使两条边不共享一个端点。最大匹配是最大大小(最大边数)的匹配。在最大匹配中,如果向其添加任何边,则该边不再是匹配。对于给定的二部图,可以有多个最大匹配。 我们为什…

【论文精读】Bipartite network projection and personal recommendation

一、Introduction 在过去的几年里,人们对复杂网络进行了大量的研究,一类特殊的网络是二部网络(bipartite network)。特点是其节点可分割为两个互不相交的子集X和Y,连接只允许存在于不同集合中两个节点之间。例如人类的…

【一致性仿真】Group-Bipartite Consensus in the Networks With Cooperative-Competitive Interactions

文章链接:Group-Bipartite Consensus in the Networks With Cooperative-Competitive Interactions 仿真图Fig3: MATLAB代码 % Group-Bipartite Consensus in the Networks With Cooperative-Competitive Interactions % Protocol Simulation Results …

C#,图论与图算法,二分图(Bipartite Graph)的霍普克罗夫特-卡普(Hopcroft Karp)最大匹配算法与源程序

二分图Bipartite graph 有没有可能通过数学过程找到你的灵魂伴侣?大概让我们一起探索吧! 假设有两组人注册了约会服务。在他们注册后,会向他们展示另一组人的图像并给出他们的描述。他们被要求选择他们愿意与之匹配的人。 所有信息都被输入…

[VLDB 2022]Butterfly Counting on Uncertain Bipartite Graphs

总结 非确定二部图上的蝴蝶结构统计,精确算法。在普通的蝴蝶结构统计上,增加了边权重,使得传统算法失效,再在这基础上定义新的统计并优化老方法。 动机 Butterfly的数量直接展示了二部图的密度,是个很重要的属性。相…

二分匹配大总结——Bipartite Graph Matchings[LnJJF]

文章目录 二分匹配——Bipartite Graph Matchings[LnJJF]认识:什么是二分图?理解:现实模型如何与二分图相互转化?如何判断能否转化?能够转化的话,如何转化? 应用:已知一个二分图&…

【一致性仿真】Fixed-time bipartite consensus of multi-agent systems with disturbances

文章链接:Fixed-time bipartite consensus of multi-agent systems with disturbances 仿真图Fig2: MATLAB代码: % Fixed-time bipartite consensus of multi-agent systems with disturbances % author:JCGUY % date:2022-04-20 clear clc…

Bipartite Graph多视图学习聚类文章总结

看了一些anchor graph和bipartite graph 的文章始终不知道他们的区别在哪里。今天总结一下这类文章。 1.能看到最早的这类关于多视图学习的文章 Large-Scale Multi-View Spectral Clustering via Bipartite Graph(AAAI-2015) 目标:we addre…

Fast spectral clustering learning with hierarchical bipartite graph for large-scale data

Fast spectral clustering learning with hierarchical bipartite graph for large-scale data 基于层次二分图的大规模数据快速谱聚类学习 abstract 传统方法:不适用大规模问题 高斯核函数 提出了一种新的基于层次二分图(SCHBG)的光谱聚…

Bipartite Graph Based Multi-View Clustering

Bipartite Graph Based Multi-View Clustering 基于二部图的多视图聚类 abstract 对于基于图的多视图聚类,一个关键问题是通过两阶段学习方案捕获共识聚类结构。具体来说,首先学习多个视图的相似性图矩阵,然后将它们融合为统一的高级图矩阵。…