2011-03-27

百度文库的对错

  上次Google Book没觉得有什么问题.
  这次,百度文库的事,才开始想其中有什么问题.
  果然,有时候还是不够中立.

  其实,百度也许在法律上并没有什么过错.
  毕竟,它不是图书的提供者,谈不上是publish的行为.
  而对于图书上传造成的影响,大体跟P2P的合法性与否差不多.

  即,对于UGC的内容,平台本身有没有责任.
  
  对于音像制品,软件产品等相对成熟的东西来说,平台的责任很难划分清楚.
  因为这些产品本身有比较明确的适用/版权说明.
  提到涉及的范围权利等.

  而图书,至少对自己身边的几本来说,并没有明确的权利划分.

  也就是说,购买图书这个行为,其实是一个并不明确的行为.
  购买的到底是什么?

  诚然,对于图书内容的引用,涉及到著作权,但是,购买之后呢?

  买到的是什么,适用于什么范围.

  以其他产品来说,可能限制了copy的数量,和copy适用的范围.
  但是,图书呢?

  没有copy.
  那阅读这个行为呢?

  比如,某人买了这本书,是只能自己看呢?还是可以借给别人看?
  想Amazon的kindle,貌似是有提供互借的.

  而日常里,相互交换阅读也是很正常的一件事情.

  对于百度文库的这种行为,其实可以理解为一个租借场所也不为过.

  于是,从法律上来说,似乎并不违法.

  但是直觉上,这又是一个不合理的事实.
  
  它的不合理在于,适用范围上.
  购买行为,所导致的所有权问题等等.
  都是并不明朗的.

  这在网络还不发达的时代可能并不严重.
  因为交流成本的问题,一本图书的流传/借阅范围并不会产生很大影响.
  于是,图书行业也并不关心这个早已存在的漏洞.
  或者说,其实有关心过,但只是对于出版行业.

  所以,才有了对图书馆博物馆之类的,能够产生大范围影响的案例进行豁免.

  但是,互联网的发展,把这个漏洞放大了.
  
  它不仅仅是个人与个人之间的交换,不仅仅是熟人与熟人之间的交换,甚至交换的增长速度可能是非线性/级数增长的.
  在这样一个环境,出版商,或者说图书版权所有者们,对于图书的流传的把握能力就失控了.

  因为这本是原本的契约里的由于含糊不清带来的漏洞.
  在对于错之间的一种存在.

  现在,百度文库的出现把这个问题彻彻底底地暴露了.
  如果说之前Google还算是一种双赢的解决方案的话,那么百度的则是完全的利用漏洞玩的一场游戏.
  
  合法但并不合理.

  其实,本质上来说,百度文库这件事情也许算是为出版业的转型提供了一个契机.
  因为只有这种血淋淋才能让那些不能接受新事物的人,不得不为寻找盈利模式而努力.

  即便百度妥协了,但是这个漏洞已经暴露出来了.
  而且,即使没有百度,事实上,盗版/网络传播的问题已经存在已久.
  出版业也不是不知道.
  
  说到底,百度也不过是把一群掩耳盗铃的家伙的遮羞布给彻底拉下来了罢了.

  作家们遇到的问题其实是寻找新的盈利模式的问题.
  在承认互联网的游戏规则下寻找新的契机的问题.

  本来,Google其实已经为他们寻找到了一种途径.
  一种算是双赢的,互联网味道十足的模式.
  可是他们拒绝了.

  在音乐行业都开始考虑转换模式,采用在线/流量等盈利的探索方式的时候,只有出版业还在坚持游离在互联网之外,似乎这样能够独善其身.

  而百度很好地出来证明他们错了.

  所以,即便这次百度低头了.
  但如果作家们依然悠然自得,希望以古老的方式,维持古老的生计.
  就很难说,作家这个行业还能存在多久.

  至少是传统出版意义上的作家.

  像起点的模式其实解决了一部分问题. 
  当然,它不能解决所有人的问题.
  毕竟,它是一个非常商业化的东西.
  
  而有些作家,可能是没那么商业化.
  或者说,需要十年磨一剑.

  说到底,好作家的定义在于,书有人看.
  而好作家如何赚钱,则可以从如何从看书的人身上赚钱出发.

  买书是一种,阅读也是一种.
  Google能把搜索编程一种商业行为.
  自然也就有人能把阅读变成一种商业行为.

  虽然,百度这次是很没下限,如有些人所说的,这是在毁灭整个行业.
  毕竟,就很多人的思维来说,在中国,能做大,而且独大,是最快最长久的盈利方式.
  因为这里从来没有垄断审查.
  从来是纯粹的"资本说话".

  但,至少百度把这一现实的问题提前摆在了世人的面前.
  怎么想,怎么做.
  
  总该会对作家们,和出版行业有所反思. 

2011-03-26

关于Hadoop

  在hadoop里写了点东西,大概也印证了有怎样的环境才有怎样的解决方案.

  确实,在hadoop里,不像在一台机器上,能比较容易的mutex操作.
  毕竟,你要mutex 的东西都不知道物理上在什么地方,甚至还存在不存在.
  所有,这个是思维要转变的地方.

  在分布式情况下,有时候create比read/write来得更浅显易懂.
  毕竟,除了delete操作,其他操作都不会影响create的行为.
  而且,当delete操作也依赖于create的某些标志性行为的时候,一切都简化到create操作上了.

  比如,要进行任何操作,先create一个标志,表明holding了这个resource.
  
  当然,这中间也还是会有些问题的.
  比如,在hadoop里,这依赖于namenode操作的正确性.
  
  某种程度上说,这种解决方法其实是利用了namenode的单点性.
  由于所有对hdfs的操作都需要汇总反馈到namenode上 ,所以,用namenode去拦截调度也是很容易想到的思路.
  毕竟,所谓的一致性,是由namenode保证的.

  但是,如果是纯粹的对等网络呢?
  比如,没有namenode的?

  其实最后还是会归结到这种有中间节点的模型上.

  比如hadoop准备改造的mapreduce模型.
  实际上就是去掉的jobtracker的这个单独的job调度节点,把它分散到开来.

  也就是实际上来所,是在tasktracker上vote一个节点作为某一个job的jobtracker罢了.

  这其实有时典型的分层思维.
  跟ip地址的掩码模式差不多.
  加一层即可虚拟出许多隔离的东西出来.

  resource manager就是这个新加的一层.

  所以,从这个程度上来说,也许并没有纯粹的对等模型.
  多少还是有一些中心节点的.
  只不过这种中心节点的特殊性不强罢了.

  就像人的选举一样.
  本质都是差不多的.
  只是由于某些原因变得有些特殊罢了.

  所以,平等这个东西,首先是建立在公平之上.
  没有公平,也就没有平等.

  话说回来,hadoop或者说map reduce这个东西,也许又是Google重新修饰了一番的东西.
  就像Bigtable的概念一样,重新包装了下,以不太直观的形式描述一个很简单的模型/思路.

  mapreduce其实就是把计算分摊到各台机器上罢了.
  即使不用hadoop,写个脚本自己分块数据自己计算汇总也是可以的.
  只不过hadoop本身解决了分块的问题.

  而所谓的map/reduce过程,则多少有些无谓?
  毕竟,redcue本身其实也是一种map过程.
  至少从hadoop的实现上来说,是这样.

  而且,hadoop本身似乎也是这么认为的.
  这个从job的combine设置以及,不显式设置reduce数目的时候,job的行为可以看出.
  
  本质上说,hadoop的reduce过程只是map的特例.
  所不同的是output出来的数量分块比较少.

  当然,从编程接口上来说,reduce跟map的区别在于,reduce是key的一个汇总.
  但其实这是map output的sort使然.
  reduce也不过是根据output结果去取罢了.

  所以,其实mapreuce本质上就是一个数据格式的转换问题.
  只不过被放到到了分布式的情况下.
  多了调度和同步的问题.

  除开这些,mapreduce也许什么都不是.  

2011-03-06

HDFS的碎碎念.

  HDFS说简单也简单,说复杂,其实也不复杂.

  它解决的主要是在集群规模大了之后,distribution的问题.
  更重要的是把disk的failure视为常态.

  因为毕竟,只是单纯的distribution的话,如NFS的也可以达到目的.
  但概念是Google提出的,它面对的问题显然不是一般人会常态遇见的.

  所以HDFS/GFS的概念主要在replication.
  
  理论上的模型也很符合直觉.
  寻找一个可用的节点,然后分发之.
  
  所不同的就是这种分发的具体实现了.

  HDFS的replication其实很简单.

  比如你upload一个local的文件到HDFS的时候,DFSClient会向namenode发起一个RPC的create请求.

  顺便说下,Hadoop的RPC其实有两套.
  一套是给各种node的用的,基于interface的reflection.
  另一个套是给DFSClient之类的,基于Invocaionhandler.
  但本质都是把方法名和参数以及连接信息什么的写到流里,然后在method.invoke()

  也许可以理解为前者是给server用的.毕竟有了local的instance.
  而诸如DFSClient的是没有instance的实现的,所以要InovcationHandler去hook.

  回到create.
  
  namenode会向FSNamesystem添加一个inode信息,同时记录一个lease.
  此时的inode为INodeFileUnderConstruction,表明是未完成的.
  而lease的作用是用来保证不重复create/以及一些超时处理.
  
  然后namenode将这个RPC的请求返回给DFSClient.
  
  DFSClient会开启一个DataStreamer去做copy and write的工作.

  首先是到RPC到namenode去申请block.
  此时的namenode会去查看FSNamesystem里的inode信息.
  
  namenode会检查inode的类型是否是INodeFileUnderConstruction,即未完成.
  然后会check下lease的信息,看时候有意外的已经replication的情况.(这个估计是以前有类似bug吧.)

  当然,在此时,一般这些check都会pass掉的.
  但,这是distribution的,所以,按照状态机来变换是最简单的事情.
   
  datanode会根据block size去选择一些datanode.
  在用DFSClient.copyfromlocal的情况下,block size是由参数fs.local.block.size决定的.
  其他情况下,是由dfs.block.size决定的.

  replicator在choose datanode的时候会根据replication的数目而略有说不同.
  当数目是<2的时候,当local也是datanode的是会被选上.
  其他情况则感觉datanode上的block数目和load做一个权衡.

  然后把选择好的naenode把block和datanode的分配信息返还给DFSClient.
  DFSClient则选择第一个datanode建立连接,把读到的数据写到这个选中的datanode上.

  在DataStreamer里还有一个ResponseProcessor的东西,在处理这个datanode返回来的ack.

  但是,这里只写往了一个datanode,那么replication怎么实现的呢?

  这个在datanode的实现了.
  datanode在经历过一些列初始化之后,会有一个DataXceiverServer去处理进来的连接.
  尤其的,没一个连接会dispatch到DataXceiver去处理.
  
  DataXceiver就是HDFS的IO操作的核心吧.
  
  当地一个datanode收到DFSClient发来的OP_WRITE_BLOCK请求时候,会调用writeBlock把读到的block写到datanode的local filesystem里.
  同时会取DFSClient传过来的datanode array信息,取第一个,然后与之建立连接,然后把把block信息和剩下的datanode写到对方的stream里.
  
  即,HDFS的replication就是通过这种级联的,pipeline方式的write扩散出去的.
  同样,ack也是一级一级地往前传递.

  至于写到datanode上的block大小限制是在DFSOutputStream里限定的.
  当写到这个数的时候会表明这是最后一个package.

  至于读则差不多.
  namenode会在返回datanode的时候稍微排序下.
  将local和local rack的往前排.
  因为client在取datanode的时候总是先取前面.

  至于local rack怎么决定的.
  这个在NetworkTopology里,没仔细看.  

爽文

去看了好东西. 坦白说,多少是带着点挑刺的味道去的. 毕竟打着爱情神话和女性题材的气质,多多少少是热度为先了. 看完之后倒是有些新的想法. 某种程度上来说,现在的年轻人或者说声音就像小叶. 只要说点贴心的话就能哄好. 也是那种可以不用很努力了. 留在自己的舒适区避难所小圈子抱团就...