用css实现下面的效果图。

方案一

<style type="text/css">
.myList1 { border: 1px solid #333; padding: 10px; }
.myList1 li { height: 20px; line-height: 20px; font-size: 12px; }
.myList2 { border: 1px solid #333; padding: 10px; }
.myList2 li { height: 20px; line-height: 20px; font-size: 16px; }
.myList3 { border: 1px solid #333; padding: 10px; }
.myList3 li { height: 20px; line-height: 20px; font-size: 12px; color: red; }
</style>
<ul class="myList1">
<li>aaaaaaaaa</li>
<li>bbbbbbbbb</li>
<li>ccccccccc</li>
</ul>
<ul class="myList2">
<li>ddddddddd</li>
<li>eeeeeeeee</li>
<li>fffffffff</li>
</ul>
<ul class="myList3">
<li>ggggggggg</li>
<li>hhhhhhhhh</li>
<li>jjjjjjjjj</li>
</ul>

方案一可以实现我们想要的效果,但它非常冗余,myList1,myList2,myList3的css设置相同,‘myList1 li’、‘myList2 li’、‘myList2 li’有部分css一致。我们需要对它们进行改进。

方案二

<style type="text/css">
.myList1, .myList2, .myList3 { border: 1px solid #333; padding: 10px; }
.myList1 li, .myList2 li, .myList3 li { height: 20px; line-height: 20px; font-size: 12px; }
.myList2 li { font-size: 16px; }
.myList3 li { color: red; }
</style>
<ul class="myList1">
<li>aaaaaaaaa</li>
<li>bbbbbbbbb</li>
<li>ccccccccc</li>
</ul>
<ul class="myList2">
<li>ddddddddd</li>
<li>eeeeeeeee</li>
<li>fffffffff</li>
</ul>
<ul class="myList3">
<li>ggggggggg</li>
<li>hhhhhhhhh</li>
<li>jjjjjjjjj</li>
</ul>

方案二和方案一思路相同,仍将模块视为完全不同彼此独立的三个类,只是对css代码做了精简工作。去除了代码冗余。

方案三

<style type="text/css">
.myList { margin-bottom: 10px; width: 300px; }
.f12 { font-size: 12px; }
.f16 { font-size: 16px; }
.red { color: red; }
.myList { border: 1px solid #333; padding: 10px; }
.myList li { height: 20px; line-height: 20px; }
</style>
<ul class="myList f12">
<li>aaaaaaaaa</li>
<li>bbbbbbbbb</li>
<li>ccccccccc</li>
</ul>
<ul class="myList f16">
<li>ddddddddd</li>
<li>eeeeeeeee</li>
<li>fffffffff</li>
</ul>
<ul class="myList f12 red">
<li>ggggggggg</li>
<li>hhhhhhhhh</li>
<li>jjjjjjjjj</li>
</ul>

方案三换了新思路,提取了更多的粒度更小类,通过类的组合实现设计图的效果。

方案二和方案三看似都是不错的解决方案,其中方案二的优势是调用简单,一个模块只需要挂一个类;方案三调用稍微麻烦,但也有效控制了冗余,代码精简。

看起来方案二和方案三都不错,但如果想实现下图的效果,又会如何呢?

需求更改

按照方案二的思路,我们需要再定义一个新的类myList4.代码清单如下:

<style type="text/css">
.myList1, .myList2, .myList3, .myList4 { border: 1px solid #333; padding: 10px; }
.myList1 li, .myList2 li, .myList3 li { height: 20px; line-height: 20px; font-size: 12px; }
.myList2 li { font-size: 16px; }
.myList3 li { color: red; }
.myList4 li { font-size: 16px; color: red; }
</style>
<ul class="myList1">
<li>aaaaaaaaa</li>
<li>bbbbbbbbb</li>
<li>ccccccccc</li>
</ul>
<ul class="myList2">
<li>ddddddddd</li>
<li>eeeeeeeee</li>
<li>fffffffff</li>
</ul>
<ul class="myList3">
<li>ggggggggg</li>
<li>hhhhhhhhh</li>
<li>jjjjjjjjj</li>
</ul>
<ul class="myList4">
<li>LLLLLLLLL</li>
<li>MMMMMMMMM</li>
<li>NNNNNNNNN</li>
</ul>

按照方案三的思路,我们无需扩展新的类,只需要在HTML的标签的class里将之前定义的类重新组合即可。

<style type="text/css">
.f12 { font-size: 12px; }
.f16 { font-size: 16px; }
.red { color: red; }
.myList { border: 1px solid #333; padding: 10px; }
.myList li { height: 20px; line-height: 20px; }
</style>
</head>
<body>
<ul class="myList f12">
<li>aaaaaaaaa</li>
<li>bbbbbbbbb</li>
<li>ccccccccc</li>
</ul>
<ul class="myList f16">
<li>ddddddddd</li>
<li>eeeeeeeee</li>
<li>fffffffff</li>
</ul>
<ul class="myList f12 red">
<li>ggggggggg</li>
<li>hhhhhhhhh</li>
<li>jjjjjjjjj</li>
</ul>
<ul class="myList f16 red">
<li>LLLLLLLLL</li>
<li>MMMMMMMMM</li>
<li>NNNNNNNNN</li>
</ul>

多用组合,少用继承

方案三借鉴了编程领域的组合的思想,将方案二中复杂的myList1、myList2、myList3等类拆分成了几个相对简单的类,其中相对稳定的部分拆分成myList类,而可能变化的部分拆成了f12类、f16类和red类。通过类的组合,很容易实现类的扩展,避免产生类爆炸。

知识延伸,面向对象编程

在面向对象中有类似上面的情况:继承和组合。

继承的思路是将一个复杂且包含变化的类,拆分成几个复杂但稳定的子类。首先明确一个抽象的父类,父类有着几乎所有的方法和属性。但使用继承的话,任何一点小的变化也需要重新定义一个类,很容易引起类的爆炸式增长,产生一大堆有着细微不同的子类。

组合的思路是将一个复杂的类分成容易产生变化的部分和相对稳定的部分,将容易变化的部分拆分出去,每一种可能的变化设计成一个个单独的类,而相对稳定部分设计成一个主体类,这样,将一个复杂的类拆分成几个简单的类,类之间没有继承关系,这遵循了面向对象设计的“单一职责”原则。将那些容易变化的类的实例赋值给主体类作为一个属性,这样就实现了类的组合。用组合方式,可以大大减少类的数量。

后记,这是我看过解释继承和组合最容易理解的说法,没有学过面对对象概念的同学可能有些地方不明白。

来源:Web前端开发修炼之道

挂多个class还是新建class —— 多用组合,少用继承的更多相关文章

  1. sau交流学习社区--在element-ui中新建FormData对象组合上传图片和文件的文件对象,同时需要携带其他参数

    今天有一个坑,同时要上传图片和文件,而且图片要展示缩略图,文件要展示列表. 我的思路是: 首先,只上传附件照片,这个直接看ele的官方例子就行,不仅仅上传附件照片,还同时上传其他参数. 然后,再做上传 ...

  2. 多用StringBuilder,少用字符串拼接

    在C#中,在处理字符串拼接的时候,使用StringBuilder的效率会比硬拼接字符串高很多.到底有多高,如下: static void Main(string[] args) { string st ...

  3. CSS之少用继承,多用组合

    下面是一段普通的代码: css: .box{ border:1px solid #ccc; font-size:12px; background:#f1f1f1; padding:10px; } ht ...

  4. idea 在新建一个class的时候可以选择继承的父类

    1.把光标放在父类名称上按alt+enter可以生成子类 2. 选中implement abstract class

  5. 多用as少用强制类型转换

    在 C# 中存在一个名叫静态类型检查的机制,这个机制可以让编译器帮助我们把类型不服的用法找出来,从而使得应用程序在运行期间加少一些类型检查的操作.但是有时候我们还是需要进行运行期类型检查,比如我们在设 ...

  6. 用尽洪荒之力学习Flask源码

    WSGIapp.run()werkzeug@app.route('/')ContextLocalLocalStackLocalProxyContext CreateStack pushStack po ...

  7. Python开发——9.面向对象编程

    一.面向对象设计(Object oriented design) 面向对象设计是将一类具体事物的数据和动作整合到一起的过程,不会要求面向对象语言编程,但如果想要构造具备对象性质和特点的数据类型,需要更 ...

  8. python+selenium之简单介绍继承

    python+selenium之简单介绍继承 一.此例简单的介绍一下继承 1.面向对象的编程带来的主要好处之一是代码的重用,实现这种重用的方法之一是通过继承机制.继承完全可以理解成类之间的类型和子类型 ...

  9. 编写高质量代码:Web前端开发修炼之道(二)

    第四章:高质量的css 1)怪异模式和标准模式 在标准模式中,浏览器根据规范表现页面:而怪异模式通常模拟老式浏览器的行为以防止老站点无法工作. 他们两者之间的差异比较典型的表现在IE对盒模型的解析:在 ...

随机推荐

  1. iOS 核心动画

    核心动画(Core Animation) : •CoreAnimation是一组非常强大的动画处理API,使用它能做出非常炫丽的动画效果,而且往往是事半功倍,使用它需要先添加QuartzCore.fr ...

  2. 网络开始---多线程---NSThread-01-基本使用(了解)(二)

    #import "HMViewController.h" @interface HMViewController () @end @implementation HMViewCon ...

  3. Objective-C的可变是如何实现的?

    Objective-C的可变是怎么实现的?      

  4. Swift面向对象基础(中)——Swift中的方法

    学习来自<极客学院> 1.定义方法需要在类型(枚举,结构体,类)里定义,不能独立定义,独立定义的是函数 2.方法要么属于该类型本身,要么是该类型的一个实例 3.不能独立执行方法,执行方法必 ...

  5. python操作db2和mysql ,ibm_db

    我需要提取mysql和db2的数据进行对比,所以需要用python对其都进行操作. python对mysql进行操作应该没什么问题,就是安装drive后就可以了,在上一篇中有讲安装python-mys ...

  6. android中实现view可以滑动的六种方法续篇(二)

    承接上一篇,上一篇中讲解了实现滑动的第五种方法,如果你还没读过,可点击下面链接: http://www.cnblogs.com/fuly550871915/p/4985482.html 这篇文章现在来 ...

  7. android中的坐标系以及获取坐标的方法

    android中有两种坐标系,分别称之为Android坐标系和视图坐标系.而对应的也有一些相关的方法可以获取坐标系中的 坐标值.只有搞清楚这些区别,才能在实现的时候不至于出错或者得不到你想要的效果. ...

  8. 你真的说的清楚ArrayList和LinkedList的区别吗

    参见java面试的程序员,十有八九会遇到ArrayList和LinkedList的区别?相信很多看到这个问题的人,都能回答个一二.但是,真正搞清楚的话,还得花费一番功夫. 下面我从4个方面来谈谈这个问 ...

  9. hibernate数据库连接池

    访问数据库,需要不断的创建和释放连接,假如访问量大的话,效率比较低级,服务器消耗大: 使用数据库连接池,我们可以根据实际项目的情况,定义连接池的连接个数,从而可以实现从连接池获取连接,用户放回到连接池 ...

  10. Mac SVN ignore 等相关

    OSX自带了SVN命令行,通过终端就可以使用了. 一.SVN ignore Mac的SVN想把node_modules 忽略,即svn status时(svn st缩写)不显示node_nodules ...