个人开发者到底选择GPL协议还是MIT协议?
为什么小米可以避开开源协议?
安卓是开源的,为什么华为还要自己造鸿蒙?
你知道史上最奇葩的开源协议吗?
这些问题,都将在这篇文章中找到答案。
目录
开源,是很多个人开发者选择的道路。
开源不仅能够帮助整个生态共同进步,也能够帮助个人开发者提升技术和名气,这一点从vue就能看出来。

但是,开源的意思并不是没有规则,全部无条件的免费提供给别人用,必须要遵循一定的规则,这个规则就是开源协议(Open Source License)。
世界上的开源协议大概有上百种,但是常用的只有5、6种,网络上的很多文章只是笼统的介绍,并没有说清楚这些协议的关键区别,以及每种协议对开发者的好处和限制。

为了帮助开发者区别这些协议,这篇文章对常见的几种协议进行介绍,包括需要遵循的原则以及目前使用这些协议的代码库。
GPL(GNU General Public License):GNU通用公共许可协议。
GPL协议的目的就是强制代码开源和免费使用。
其最大的特点就是“开源的传染性”。也就是说,假设某公司使用了具有GPL协议的代码库,那么他理论上也必须把自己的代码库开源。
注意,这里是理论上。
实际上,大公司可以有很多方法避开这个限制。
比如,2015年的时候,小米被指责违反了GPL协议,MIUI系统是基于Android开发的,而内核Linux遵循的是GPL协议,那么小米也必须对自己的MIUI系统进行开源。

但是小米方面给出的答复是“很快就会开源”。这个很快,就慢慢拖着,反正我也不否认未来会开源。
另外,大公司还会选择为自己维护一套闭源的商业代码。
比如最著名的AOSP (Android Open-Source Project) 和Android。
AOSP是开源的安卓系统,而Android这个词已经变成了谷歌的一个商标,以及附加了GMS等一些软件的大系统。

什么意思呢,我们认为开源的那套系统,实际上就像一个毛坯房,而真正附加了谷歌全家桶等软件的Android,是精装房,精装的部分是不开源的。
所以华为一定要自己基于AOSP开发一套操作系统,你要不这么干的话,只要谷歌禁止你使用Android,马上就死。
说个笑话,GPL协议没有限制你卖钱。
也就是说理论上,你可以把原汁原味的开源linux系统卖给别人,当然有没有买家就另说了。

由于GPL协议的“开源传染性”,一些公司肯定无法接受将自己的代码开源出去,这还怎么赚钱呢?
于是出现了LGPL( GNU Lesser GPL),也就是限制更少(针对想闭源卖钱的公司)的GPL。
如果公司只是想白嫖某个LGPL协议的代码库,而不需要对其及进行修改,那就可以使用此协议。

具体来说就是。
如果使用动态链接LGPL代码库,则你不需要开源。
如果使用静态链接,则你可以通过封装一层的方式避免开源,可以简单理解为只需要开源直接调用LGPL库的那部分代码就可以了。
是不是有些难以理解,没关系,我们举个例子。
假设有一个LGPL库,名为LibA,现在你在源文件main.cpp中使用了此库,如下:
int main() {
LibA.init();
LibA.DoSomething();
}
按照LGPL协议,你的这个源文件必须要开源,因为它直接调用了LibA的代码。
如何避免呢?封装!
你再写一个封装文件wrapper.cpp,如下:
void my_libA_init() {
LibA.init();
}
void my_libA_DoSomething() {
LibA.DoSomething();
}
接下来,在你的main.cpp中调用你的封装文件,相当于间接调用LibA:
int main() {
my_libA_init();
my_libA_DoSomething();
}
那么,你只需要开源wrapper.cpp,而不需要开源main.cpp了,这样就可以隐藏上层逻辑,也就能够作为商业软件卖钱了。
著名的GUI开发框架Qt使用了LGPL协议。
MIT(The Massachusetts Institute of TechnologyLicense,麻省理工学院许可协议)是众多协议条款中,被广泛使用的其中一种。与其他常见的软件许可协议相比,MIT是相对宽松的软件许可协议。
MIT协议允许你任意的使用、复制、修改原MIT代码库,随便你卖钱还是开源,唯一需要遵循的原则就是在你的软件中声明你也使用的是MIT协议就行了。
而很多的公司企业在选用开源产品的时候都首选MIT协议,因为可以完全控制这些第三方的代码,在必要的时候可以修改或者二次开发。

UI框架VUE、脚本语言Lua使用的就是MIT协议。
BSD协议几经变种,和MIT协议区别已经不大,唯一的小区别是BSD要求开发者不能利用前人的名义做宣传。比如我不能以某某升级版,某某加强版的名义来宣传我的软件。
MIT和BSD协议有一个特点:简洁。
这个特点具有两面性。
一方面,作为个人开发者,可以放心的使用MIT或BSD协议而不太需要担心背后的法律风险。
另一方面,大公司在开源自己软件时,会担心由于“过度宽松”导致产生一些法律纠纷。
因此,Apache协议出现了。
在保持较为宽松的开源基础上,加上了一些避免法律冲突的限制。
比如,要求在每个许可文件中,必须保留再分发代码中的任何原始著作权、专利、商标等。
因此,大公司往往倾向于使用Apache协议而不是稍微模糊的MIT协议。
百度的深度学习框架PaddlePaddle使用了Apache协议。

如果你觉得上面的协议没一个自由的,你崇尚绝对的自由开源,那么这条协议就太适合你了。
WTFPL协议是目前最奇葩的协议,奇葩在两点。
第一点是,这个协议实际上没有任何内容,这里是这个协议的内容。

鉴于这里面敏感词太多我就不逐字翻译了。
大致意思就是:你想干什么就干什么吧,你可以随便改代码,你也可以随便改协议内容,。
第二个奇葩点在于。
这个协议是已经被认证了的协议......
你敢相信,这个奇葩协议是一个正儿八经的正规军。
现在,你搞清楚不同开源协议之间的区别了吗?
我正在编写一个包含C扩展的gem。通常当我写一个gem时,我会遵循TDD的过程,我会写一个失败的规范,然后处理代码直到它通过,等等......在“ext/mygem/mygem.c”中我的C扩展和在gemspec的“扩展”中配置的有效extconf.rb,如何运行我的规范并仍然加载我的C扩展?当我更改C代码时,我需要采取哪些步骤来重新编译代码?这可能是个愚蠢的问题,但是从我的gem的开发源代码树中输入“bundleinstall”不会构建任何native扩展。当我手动运行rubyext/mygem/extconf.rb时,我确实得到了一个Makefile(在整个项目的根目录中),然后当
请帮助我理解范围运算符...和..之间的区别,作为Ruby中使用的“触发器”。这是PragmaticProgrammersguidetoRuby中的一个示例:a=(11..20).collect{|i|(i%4==0)..(i%3==0)?i:nil}返回:[nil,12,nil,nil,nil,16,17,18,nil,20]还有:a=(11..20).collect{|i|(i%4==0)...(i%3==0)?i:nil}返回:[nil,12,13,14,15,16,17,18,nil,20] 最佳答案 触发器(又名f/f)是
我已经在Sinatra上创建了应用程序,它代表了一个简单的API。我想在生产和开发上进行部署。我想在部署时选择,是开发还是生产,一些方法的逻辑应该改变,这取决于部署类型。是否有任何想法,如何完成以及解决此问题的一些示例。例子:我有代码get'/api/test'doreturn"Itisdev"end但是在部署到生产环境之后我想在运行/api/test之后看到ItisPROD如何实现? 最佳答案 根据SinatraDocumentation:EnvironmentscanbesetthroughtheRACK_ENVenvironm
我们的git存储库中目前有一个Gemfile。但是,有一个gem我只在我的环境中本地使用(我的团队不使用它)。为了使用它,我必须将它添加到我们的Gemfile中,但每次我checkout到我们的master/dev主分支时,由于与跟踪的gemfile冲突,我必须删除它。我想要的是类似Gemfile.local的东西,它将继承从Gemfile导入的gems,但也允许在那里导入新的gems以供使用只有我的机器。此文件将在.gitignore中被忽略。这可能吗? 最佳答案 设置BUNDLE_GEMFILE环境变量:BUNDLE_GEMFI
我正在检查一个Rails项目。在ERubyHTML模板页面上,我看到了这样几行:我不明白为什么不这样写:在这种情况下,||=和ifnil?有什么区别? 最佳答案 在这种特殊情况下没有区别,但可能是出于习惯。每当我看到nil?被使用时,它几乎总是使用不当。在Ruby中,很少有东西在逻辑上是假的,只有文字false和nil是。这意味着像if(!x.nil?)这样的代码几乎总是更好地表示为if(x)除非期望x可能是文字false。我会将其切换为||=false,因为它具有相同的结果,但这在很大程度上取决于偏好。唯一的缺点是赋值会在每次运行
这似乎非常适得其反,因为太多的gem会在window上破裂。我一直在处理很多mysql和ruby-mysqlgem问题(gem本身发生段错误,一个名为UnixSocket的类显然在Windows机器上不能正常工作,等等)。我只是在浪费时间吗?我应该转向不同的脚本语言吗? 最佳答案 我在Windows上使用Ruby的经验很少,但是当我开始使用Ruby时,我是在Windows上,我的总体印象是它不是Windows原生系统。因此,在主要使用Windows多年之后,开始使用Ruby促使我切换回原来的系统Unix,这次是Linux。Rub
我正在玩HTML5视频并且在ERB中有以下片段:mp4视频从在我的开发环境中运行的服务器很好地流式传输到chrome。然而firefox显示带有海报图像的视频播放器,但带有一个大X。问题似乎是mongrel不确定ogv扩展的mime类型,并且只返回text/plain,如curl所示:$curl-Ihttp://0.0.0.0:3000/pr6.ogvHTTP/1.1200OKConnection:closeDate:Mon,19Apr201012:33:50GMTLast-Modified:Sun,18Apr201012:46:07GMTContent-Type:text/plain
我正在阅读一本关于Ruby的书,作者在编写类初始化定义时使用的形式与他在本书前几节中使用的形式略有不同。它看起来像这样:classTicketattr_accessor:venue,:datedefinitialize(venue,date)self.venue=venueself.date=dateendend在本书的前几节中,它的定义如下:classTicketattr_accessor:venue,:datedefinitialize(venue,date)@venue=venue@date=dateendend在第一个示例中使用setter方法与在第二个示例中使用实例变量之间是
无论您是想搭建桌面端、WEB端或者移动端APP应用,HOOPSPlatform组件都可以为您提供弹性的3D集成架构,同时,由工业领域3D技术专家组成的HOOPS技术团队也能为您提供技术支持服务。如果您的客户期望有一种在多个平台(桌面/WEB/APP,而且某些客户端是“瘦”客户端)快速、方便地将数据接入到3D应用系统的解决方案,并且当访问数据时,在各个平台上的性能和用户体验保持一致,HOOPSPlatform将帮助您完成。利用HOOPSPlatform,您可以开发在任何环境下的3D基础应用架构。HOOPSPlatform可以帮您打造3D创新型产品,HOOPSSDK包含的技术有:快速且准确的CAD
导读:随着叮咚买菜业务的发展,不同的业务场景对数据分析提出了不同的需求,他们希望引入一款实时OLAP数据库,构建一个灵活的多维实时查询和分析的平台,统一数据的接入和查询方案,解决各业务线对数据高效实时查询和精细化运营的需求。经过调研选型,最终引入ApacheDoris作为最终的OLAP分析引擎,Doris作为核心的OLAP引擎支持复杂地分析操作、提供多维的数据视图,在叮咚买菜数十个业务场景中广泛应用。作者|叮咚买菜资深数据工程师韩青叮咚买菜创立于2017年5月,是一家专注美好食物的创业公司。叮咚买菜专注吃的事业,为满足更多人“想吃什么”而努力,通过美好食材的供应、美好滋味的开发以及美食品牌的孵