谷歌买房面试题

请听题:

谷歌校园招聘面试题

现在北京有一套房子,价格200万,假设房价每年上涨10%,一个软件工程师每年固定能赚40万。如果他想买这套房子,不贷款,不涨工资,没有其他收入,每年不吃不喝不消费,那么他需要几年才能攒够钱买这套房子?

A, 5年

B, 7年

C, 8年

D, 9年

E, 永远买不起

答案是E,解题过程请看下表。

工作年数 不吃不喝存款 房价 资金缺口 买房的希望 1 40万 220万 180万 2 80万 242万 162万 3 120万 266.2万 146万 4 160万 292.82万 132万 5 200万 322.102万 122万 6 240万 354.3122万 114万 7 280万 389.74342万 109万 8 320万 428.717762万 108万 9 360万 […]

新版twitter背后的技术

如果要评2010最牛逼的网站改版,除了豆瓣就是Twitter了(开个玩笑)。那天看了新版twitter的介绍视频,相当兴奋,那种感觉就像04年看到gmail。面对未知的新时代,一部分人在畅想,一部分人在抵触,只有小部分人在行动。Twitter很快交出了他们的答卷。

今天看到Twitter官方发表的博文“The Tech Behind the New Twitter.com”,总结了新版twitter背后的技术,值得一读。(下面的内容不是翻译,是我的理解)

API客户端 新版背后的一个重要的架构上的改变是像其它第三方客户端一样,Twitter自己也开始基于API开发,唯一不同是他们可以使用更多资源。同时对访问API做了诸多优化,原文提到的“highly optimized JSON fragment cache”。

评论:这种方式是很多技术团队都想实现的,但碍于原有架构的历史问题,下不了决心彻底改变它。但未来要满足各种终端上各种形式应用的开发需求,这种架构是最灵活的。

The Javascript API 对应后端的API架构,前端自然需要一个很给力的Javascript库实现和后端的数据交互。Twitter内部用到一个库叫@anywhere (http://platform.twitter.com/js-api.html),它提供的功能: 1. 负责和API交换数据。文档里可以看到提供了丰富的接囗。 2. 提供一个客户端的缓存策略(保存在本地的内存和localStorage中)。@ded不久前写的“JavaScript Cache Provider”其实透露了一些细节。 3. 提供一个事件通知机制,当UI发生变化,相应处理组件能够立即响应。

评论:从中可以看到Twitter前端架构的设计思路,跟后端充分对接,建立业务级的通用接囗层,提供通用处理机制解藕,保持代码的模块化。这个路子很对,很值得借鉴。

页面管理 新版的一个项目目标就是让页面导航更简单更快。它是利用URL hash建立一套浏览器端的页面路由系统。这个具体要等到用上新版后看一看。

评论:像GMail那种,用URL hash做页面切换,管理起来还是很复杂的。等用上新版后要好好分析一下代码。

渲染堆栈(The Rendering Stack) 新版Twitter的页面都是在前端渲染的,但在不支持Javascript的情况下,后端也需要一个渲染系统。他们前后端用的模板系统都是Mustache,这样前后端可以保持一致,利用Mustache将API对象转成HTML代码。另外,针对DOM操作还做了诸多优化,如事件处理都是用事件代理机制实现,提高组件的重用性,尽可能减小repaint提高页面渲染性能等。

评化:Mustache是开源的模板系统,支持各种语言。我原来认为它有点重,并没有在项目中用过它。但如果真要做一个所有页面切换都是Ajax的应用,Mustache是首选。

内联媒体(Inline Media) 新版Twitter整合了很多第三方内容,从URL中判断如果是像kiva,vimeo这样的合作方,会利用基于oEmbed标准的JSON-P方式,从合作方的接囗中抓取内容。如果判断是来自TwitPic的图片或来自Youtube的视频,就直接显示出来。从视频中可以看到,交互方式很酷。

开源 Twitter的前端开发大量用到开源技术,像jQuery, Mustache, LABjs, Modernizr和大量jQuery插件。这么做的好处是一方面可以将重心放在前端应用的创新上,另一方面对开源社区的发展也是一种推动。自己在项目中积累的一些技术也会开源。

评论:我非常赞同这样。不要重复造轮子,尤其像浏览器级的基础功能库,jQuery,YUI已经做的很成熟了,需要做的应该是在没有或没有成熟的开源技术解决的领域上,通常更多在应用层面上需要建立适合自己产品的各种功能库和框架机制。

Twitter前端团队成员,可以关注一下: Ben Cherry @bcherry

http://www.adequatelygood.com/

Marcus Phillips @mracus

[…]

如何在大海中上网?

1.

9月7日,程序员Justin Watt登上远洋货轮Cap Cleveland号,随船旅行。

这艘船从费城出发,目的地是新西兰的奥克兰,将在大海中航行28天。

一路上,Justin Watt都在更新自己的网志,分享旅行照片。根据最新文章,24小时之前,他的位置是在北纬15.248547度、西经74.746492度,也就是牙买加与哥伦比亚之间的加勒比海上。

但是,这条船没有安装上网设备。他怎么能在大海中上网呢?

2.

今天,他终于揭开了谜底,原来用的是海事卫星上网。

我一向以为,海事卫星是很贵的东西。看完他的文章才知道,其实个人完全可以负担。按照他说的做,你也能在大海中上网。

3.

先介绍一下,什么是海事卫星?

1979年,国际海事组织(IMO)决定成立”国际移动卫星组织”,为大海中航行的船只提供卫星通信。这个组织发射的卫星,就叫做海事卫星。

1999年,该组织脱离IMO,变成一家私人控股的商业公司,名称为Inmarsat, 面向全世界提供卫星通信服务。所以,严格地说,它的卫星已经不能再叫做海事卫星,而是普通的商业卫星了。2005年,这家公司在伦敦证券交易所上市。2009年的营业收入是10.38亿美元,净利润是1.53亿美元。

目前,inmarsat公司一共有三颗卫星,除了极地以外,覆盖地球上所有地区。

这三颗卫星组成了一个局域网,inmarsat把这个局域网叫做BGAN(宽带全球区域网,Broadband Global Area Network)。当你的电脑连上卫星的时候,不是直接连入互联网,而是通过BGAN这个局域网的网关,再与互联网进行通信。举例来说,三颗卫星的IP地址是http://192.168.1.35/,上线后可以访问这个地址的web界面,查看卫星状态。

4.

为了卫星上网,你首先必须搞到一个卫星modem,这样才能连上卫星。

BGAN的modem,都是专用型号,也就是说,它只能用来连海事卫星。目前,最低端的型号是Wideye Sabre 1,价格为1138美元。

它的体积是259mm(长)x159mm(宽)x58mm(高),重量1.65公斤,还是相当便携的。内置锂电池,不使用外置电源的情况下,能够待机36小时,连续工作1~3小时。机身上有电话的RJ-11接口和局域网的10Mbps接口,可以满足语音和数据通信。

它的上行速率是240kbps,下行速率是384kbps。根据Justin Watt的测试,可以跑满,所以勉强还能算宽带。

5.

但是,对于普通人来说,1000多美元/个的modem,还是太贵了。不可能为了一次长途旅行,就去买一个。

怎么办呢?

很简单,买不起就租啊。

你在google里搜索”BGAN rental“,会得到很多结果。Justin Watt选择了SatellitePhoneStore.com,那里的租金价格,已经是普通人可以承受的水平了。Wideye Sabre 1的月租金是155.95美元,周租金是39.95美元,日租金是6.95美元。

需要注意的是,这只是设备的租金,上网费另行收取。每MB的价格是6~8美元(根据预付费的不同而不同)。

以Justin Watt为例,他旅行一个月,设备租金是155.95美元,另外又花了150美元,购买了25MB的流量,总计支出300美元左右,也就是2000元人民币。对于个人来说,这个价格不便宜,但远远称不上高不可攀。在某些特殊情况下,这样的成本可以换来一个月不管何时何地、始终与外界保持联系,应该还是值得的。

6.

最后,总结一下使用海事卫星上网的步骤。

  第一步:来到室外。

  第二步:打开笔记本电脑。

  第三步:打开卫星modem。

  第四步:用网线将两者连起来。

  第五步:在笔记本上,打开浏览器,访问网关http://192.168.1.35/。按照提示,键入用户名和密码。

  第六步:选择Setup选项卡,点击”Register Network”链接,将设备在网络中登记。

[…]

一个用C++实现的Dispatcher(三)

eBen给《一个用C++实现的Dispatcher(二)》提出了一些非常好的问题,修正了一些细节。但有一点需要稍加讨论一下:那几个new,可能某些做服务器端程序的人会受不了. handlers倒是可以做成static的.所有对象共用一份就可以了.

这个问题在实现这个dispatcher的时候,有人提出来过,但我依然坚持我的选择。

似乎做过服务器应用的人对性能和内存都有着特别的敏感,我也做过,我也一样。如果每个请求都去创建dispatcher的话,不仅是内存,还有创建的成本在里面。

但是,我们为什么要每次都去创建呢?如果一次创建好,就存放在内存中,不就没有这样的问题了。

把handlers设计成static,不是一个好的设计,这样的话,这个dispatcher类本身就是有状态的了,一个对象的误操作很容易就影响到另外的对象。一个好的设计应该是尽可能无状态的,这也是全局变量不受欢迎的一个原因,杀伤力太大,且错误不好定位。

之所以有人曾经给我提出过这个问题,因为他们的代码里有太多这样的代码:void Main::run() {    …    MsgDispatcher dispatcher;    dispatcher.dispatch(&msg);    …}

这样的用法去使用这个dispatcher当然会有他们所担心的问题。解决起来很容易,把这个局部变量提取出来,比如做成类成员。

我们现在知道了正确的做法是只初始化一次。不过,如果这是一个内层的代码就稍微麻烦一些了,即便这个类修正好了,我们不能保证这个代码在外层只调用了一次。面对遗留代码时,事往往不如意。

在这种情况下,我会为这个dispatcher实现一个singleton:class MsgDispatcherSingleton {public:    static MsgDispatcher* getDispatcher() {        if (NULL == dispatcher) {            dispatcher = new MsgDispatcher;            …        }

        return dispatcher;    }private:    MsgDispatcherSingleton() {}

    static MsgDispatcher* dispatcher;}

MsgDispatcher* MsgDispatcherSingleton::dispatcher = NULL;

需要知道的是,这是为了遗留代码所做的妥协,并不是我们真正设计的一部分。所以,我把它独立出来,如果有一天遗留代码被消除了,这个类也该随风而去。

[…]

腾讯收购Discuz的原因分析

一、组建广告联盟,抵抗百度广告联盟和阿里妈妈。也有可能嵌入搜搜,与站长分成。

二、发展电子商务,阻击淘宝及淘宝客。应对阿里巴巴收购phpwind。将拍拍与Discuz对接,仿照阿里巴巴用phpwind打造大淘宝。

三、将QQ号与论坛捆绑,采用OpenID模式,用户可通过QQ号登陆discuz论坛,增加QQ用户数量的同时增加QQ粘性。最终使QQ成为网络身份证。(因为涉及到QQ号的安全,腾讯不会让用户直接在别的平台输入账号和密码。)

四、用来推广微博,将Discuz和微博整合,以此来对抗新浪微博。同时也需要应对新浪微博开放接口。

五、Manyou SNS开发平台的利用,用来推广腾讯游戏和自己的SNS做整合。

一个用C++实现的Dispatcher(二)

遗留代码就是遗留代码,总会有一些让人意想不到的地方,原以为所有消息都是由一个类(MsgHandler)处理的,可事实上,不是。if (msg->id == "open") {    MsgHandler handler(msg);    handler.open();} else if (msg->id == "close") {    MsgHandler2 handler(msg);    handler.close();} else if (…) {    …} else {    // exception handler    …}

上面的代码里面只有消息处理类的名字不同,其它的处理完全相同。不过,这样就让之前那个dispatcher就显得势单力薄。解决程序设计的问题,有一个很好用的处理手法:加个间接层。于是,class DispatchHandler {public:    virtual void execute(Msg* msg) = 0;};

对于前面的两种类型,道理上来说,我们需要分别为两个类型(MsgHandler和MsgHandler2)分别编写对应的子类。不过,我们用的是C++,是的,模板:template<typename T>class DispatchHandlerImpl : public DispatchHandler {    typedef void (T::*Func)();public:    DispatchHandlerImpl(Func sourceHandler)        :handler(sourceHandler) {}

    void execute(Msg* msg) […]

一个用C++实现的Dispatcher(一)

又和一个团队合作,面前又摆着一堆分发的代码,不同的是,这次用的是C++:if (msg->id == "open") {    MsgHandler handler(msg);    handler.open();} else if (msg->id == "close") {    MsgHandler handler(msg);    handler.close();} else if (…) {    …} else {    // exception handler    …}

不要问我为什么不是每个消息对应一种处理类,要是知道为什么,就不是遗留代码了。于是,我们尝试着用C++写了一个dispatcher。下面是这个dispatcher的声明:#include <map>

typedef void (MsgHandler::*handlerFunc)();

class MsgDispatcher {public:    …    void dispatch(Msg* msg);private:    std::map<string, handlerFunc> handlers;};

因为要处理遗留代码,这里用到了指向成员函数的指针,也就提高了理解这段代码的门槛。具体实现如下:void MsgDispatcher::dispatch(Msg* msg) {    handlerFunc func = this->handlers[msg->id];    if (func) {        MsgHandler […]

自由门和GFW一样内置过滤系统

今天刚刚知道了一件事情,原来自由门软件也有过滤系统的,感觉挺搞笑的.

话说前几天豆瓣上的网友发帖说自己网站打不开,无论opera、chrome、firefox、IE都打不开,打开后网页是空白,查看网页源代码也是空白.我测试了下发现Firefox能打开,但是IE和chrome打不开(当时我Firefox用的GAppProxy代理,其他用的门代理),其博客模板也看不出来什么毛病,后来还是楼主自己发现了问题说:有新发现,用自由门无法访问,带TOR后火狐可以访问。我很纳闷它被自由门认证了,这也太离谱了吧.一位网友来了句”是不是你的域名x太多了被当黄色网站了”. 经过楼主的验证发现:凡是域名中包含了3个以上的x,或是有sex都无法用门访问,过滤系统确实不如GFW来的自能.楼主悲剧当中.

以下为测试自由门访问内容 可以访问: http://melo-x.blogspot.com/ http://suz-xx.blogspot.com/

无法访问: http://xxx.blogspot.com/ http://btbgtfxxx.blogspot.com/ http://xxxx.blogspot.com/ http://xxxxx.blogspot.com/ http://sexandthebeach.blogspot.com/ http://oxbridgesex.blogspot.com/ http://sex.blogspot.com/

按照”被时代”的说法应该是被色情网站了. 这给我们提了一个醒:域名XX两下就够了.再多了会后悔的.

Copyright ©2010 OceanBan的空间 All Rights Reserved. […]

一个用C实现的Dispatch框架

用条件语句做分发是一件很常见的事:switch(msg->id) {    case ID1:         ID1Handler(msg);        break;    case ID2:        ID2Handler(msg);        break;    …}

条件稍微多一些点,函数就会变得冗长不堪。有的团队会直接用if..else,进行判断,于是我们有幸知道了,VC不支持超过128个的选择分支。为了让这种代码的可维护性更好,我们做了一些尝试。

下面定义了一个dispatcher:BEGIN_DISPATCHER(MSG, ID, MsgHandler)    DISPATCH_ITEM(ID1, ID1Handler)    DISPATCH_ITEM(ID2, ID2Handler)END_DISPATCHER(PCU_DisasterHandler)

首先,用BEGIN_DISPATCH_MAP定义了这个dispatcher的名字(MSG),用做分发键值的类型(ID)和处理函数的类型(MsgHandler)。接下来,用DISPATCH_ITEM定义了几个分发项,也就是说,如果传入的值是ID1,会用ID1Handler进行处理,如果是ID2,则对应着ID2Handler。最后,用END_DISPATCH_MAP定义了一个错误处理函数。这样的话,就把使用的时候,就不必额外去做判空的操作了。这是Null Object模式的一种体现。

这个dispatcher的使用方式如下:dispatch(to(MSG), with(msg->id))(msg);

这段代码的含义是使用MSG这个dispatcher,根据msg->id找到对应的处理函数,传入的参数是msg。

这个dispatch框架的实现如下:#include <string.h>#define SIZE_OF_ARRAY(array) sizeof(array)/sizeof(array[0])

/* dispatcher definition */

#define __DISPATCHER_NAME(name) __dispatcher_##name#define __DISPATCH_ITEM_NAME(name) __dispatch_item_##name#define __IsMatched(target, source) (0 == memcmp(&target, &source, sizeof(target)))

#define BEGIN_DISPATCHER(name, key_type, handler_type)     struct __DISPATCH_ITEM_NAME(name) {        key_type key;        […]

Category

Archives