??xml version="1.0" encoding="utf-8" standalone="yes"?>久久国产精品二国产精品,亚洲欧美精品一区久久中文字幕 ,日本免费一区二区久久人人澡http://www.shnenglu.com/chenlq/archive/2012/05/10/174476.html陈良乔——《我的第一本C++书?/dc:creator>陈良乔——《我的第一本C++书?/author>Thu, 10 May 2012 09:59:00 GMThttp://www.shnenglu.com/chenlq/archive/2012/05/10/174476.htmlhttp://www.shnenglu.com/chenlq/comments/174476.htmlhttp://www.shnenglu.com/chenlq/archive/2012/05/10/174476.html#Feedback0http://www.shnenglu.com/chenlq/comments/commentRss/174476.htmlhttp://www.shnenglu.com/chenlq/services/trackbacks/174476.html #include // 旉工具 #include // U程 #include // 条g变量 #include // 互斥 using namespace std; using namespace std::chrono; // 条g变量 condition_variable cond; // 互斥 mutex m; // 表示条g的共享资? bool morning = false; // (g)查是否到?jin)关灯的旉? void check() { // 记录开始时? auto start = system_clock::now(); do { // 当前U程休眠1000毫秒 this_thread::sleep_for(milliseconds(1000)); cout<<"it is still night."<<endl; } // (g)查是否已l到?jin)关灯的时? // q里用seconds(4)表示路灯持箋4U? while ( system_clock::now() < start + seconds(4)); // 到达关灯旉Q锁定互斥对象, // 修改表示条g的共享数据morning lock_guard lk(m); cout<<"it is morning."<<endl; morning = true; // 用notify_one()通知另外的线E,条g已经发送变? cond.notify_one(); } /// 关灯U程 void turnoff() { // 锁定互斥对象Q访问表C条件的׃n资源morning unique_lock lk(m); // 构造一个@环,只要条g没有满 // ׃直执行条件变量的wait()Ҏ(gu)Q让当前U程{待 while(!morning) { cond.wait(lk); } // 条g满。执行关灯动? cout<<"turn off the light."<<endl; } int main(int argc, char* argv[]) { // 创徏两个U程Q分别执行检查和关灯的动? thread c(check); thread t(turnoff); c.join(); t.join(); return 0; } 从这个例子中Q我们可以得到这样一些用条件变量的要点Q? 条g变量L需要与一个表C条件的׃n资源以及(qing)对这个共享资源进行访问控制的互斥对象。这是我们在程序的开始部分定义的morningQm和cond? // 条g变量 condition_variable cond; // 互斥 mutex m; // 表示条g的共享资? bool morning = false; q三者几乎L怼同时出现? 在一个线E中Q我们需要在条g满的时候修改表C条件的׃n资源的|然后用条件变量的notify_one()或者notify_all()通知正在{待的线E。这是 // 到达关灯旉Q锁定互斥对象, // 修改表示条g的共享数据morning lock_guard lk(m); cout<<"it is morning."<<endl; morning = true; // 用notify_one()通知另外的线E,条g已经发送变? cond.notify_one(); 而在另外一个线E中Q我们需要构造一个以׃n资源为条件的无限循环Q当条g无法满Ӟq条g变量的wait()或者wait_until(){函数进行等待,直到条g得到满Q@环结束? // 锁定互斥对象Q访问表C条件的׃n资源morning unique_lock lk(m); // 构造一个@环,只要条g没有满 // ׃直执行条件变量的wait()Ҏ(gu)Q让当前U程{待 while(!morning) { cond.wait(lk); } ȝhQ条件变量简化了(jin)对表C条件的׃n资源的访问,也省M(jin)对共享资源的频繁的锁操作Q进一步提高了(jin)效率?/mutex>

]]>
用C++11 FAQ中文版学?fn)C++11Q轻松而简单!http://www.shnenglu.com/chenlq/archive/2012/05/01/173326.html陈良乔——《我的第一本C++书?/dc:creator>陈良乔——《我的第一本C++书?/author>Tue, 01 May 2012 03:01:00 GMThttp://www.shnenglu.com/chenlq/archive/2012/05/01/173326.htmlhttp://www.shnenglu.com/chenlq/comments/173326.htmlhttp://www.shnenglu.com/chenlq/archive/2012/05/01/173326.html#Feedback0http://www.shnenglu.com/chenlq/comments/commentRss/173326.htmlhttp://www.shnenglu.com/chenlq/services/trackbacks/173326.html

]]>
C++品Q她来听我的演唱?x)——C++11中的随机数、线E?thread)、互?mutex)和条件变?condition)http://www.shnenglu.com/chenlq/archive/2011/11/12/159981.html陈良乔——《我的第一本C++书?/dc:creator>陈良乔——《我的第一本C++书?/author>Sat, 12 Nov 2011 02:29:00 GMThttp://www.shnenglu.com/chenlq/archive/2011/11/12/159981.htmlhttp://www.shnenglu.com/chenlq/comments/159981.htmlhttp://www.shnenglu.com/chenlq/archive/2011/11/12/159981.html#Feedback3http://www.shnenglu.com/chenlq/comments/commentRss/159981.htmlhttp://www.shnenglu.com/chenlq/services/trackbacks/159981.htmlhttp://imcc.blogbus.com/logs/172675220.html
 

在新颁布的C++新标准C++11中,最令hȀ动h?j)的Q我想不是auto关键字,也不是Lambda表达式,而是其中的对q行计算的支持——新的线E库(thread)的加入?/p>

多核?j)CPU的普?qing)应用,C++的主要应用领域,服务器程序,高性能计算{等Q都对ƈ行计提Z(jin)新的要求Q而这ơC++中全新添加的U程库,是 对这一势的应寏V现在,C++E序员可以轻村֜~写多线E的E序Q而无需借助pȝAPI或者是W三方程序库的支持。线E库的加入给C(j)++带来的变化,? 异于 194Q翻w的E序员们把歌唱?/p>

C++11中的U程库,很大E度上直接来自boostq块C++的试验田Q其基本架构和组仉完全相同Q如果你是一个boostU程库的使用者,? 么在C++11中,你会(x)感觉到是回到?jin)老家一P到处都是熟h。而如果你是一个完全的新手Q也不要紧,C++11中的U程库非常简单,M人都可以L? 手,我就是这P但是要深IӞq得好好学习(fn)?/p>

下面是一个简单的例子Q用C(jin)U程库中的线E(threadQ?互斥QmutexQ?条g变量QconditionQ,来模拟一个演׃(x)的入场检的场景Q另外,Z(jin)模拟观众Q用C(jin)C++11中的新的随机数的产生Q模拟一个正态分布的访客人群。不说了(jin)Q还是看代码Q?/p>

#include <iostream>
#include <queue>
#include <vector>
// 随机?br />#include <random>
// q里Q我使用?jin)boost实现的线E库Q如果你的编译器已经支持C++11Q则使用<thread>是一L(fng)
#include <boost\thread.hpp>
#include <boost\thread\locks.hpp>
#include <boost\thread\condition.hpp>

using namespace std;
using namespace boost;

// ׃n资源和互斥对?br />mutex mtx;
bool finish = false;  // 表示观众到来是否l束

// 观众Q主要是Z(jin)表示(g)过E中的检耗费旉
class viewer
{
public:
    void check()
    {
        // U程{待
        posix_time::milliseconds worktime(400); 
        this_thread::sleep(worktime);   
    }
    void arrival(int t)
    {
        posix_time::seconds arrtime(t); 
        this_thread::sleep(arrtime);   
    }
};
// (g)口
// 它有一个队列,用于保存到来的观众,q且用一个线E来处理队列中的观众
class gate
{
    typedef boost::mutex::scoped_lock scoped_lock;
public:
    gate():count(0),no(0){};
    // 启动U程
    void start(int n)
    {
        no = n;
        t = thread(&gate::check,this);
    }

    // (g)?br />    void check()
    {
        // 无限循环Q知道观众数?且不?x)有新的观众到?br />        while(true)
        {
            viewer v;
            {
                // 锁定互斥对象Q开始访问对?br />                scoped_lock lock(m);
                if(0==vque.size())  // 如果队列为空
                {
                    {
                    // 判断是否q会(x)有新的观众到来,也即是表C到辄U程是否l束
                    scoped_lock finlk(mtx);
                    if(finish)
                        return; // 如果已经l束Q检也同样l束
                    }
                    // 如果观众Cؓ(f)0Q则{待新的观众的到?br />                    while(0 == vque.size())
                    {   
                          // q里的wait()是条件变量的关键Q它?x)先是否lock所锁定的互斥对象m一定时_(d)
                          // 然后再次锁定Q接着q行Q?==vque.size()Q的判断。如此往复,知道size不等?Q?br />                          // 循环条g无法满而结束@环,q里表达的条件就是,只有size!=0Q也是队列中有
                          // 观众才l向下?
                          cond.wait(lock);
                    }
                }
                // 从对列中获得观众Q对其进行检?
                v = vque.front();
                vque.pop();
                cond.notify_one(); // q里是通知d观众的进E,表示队列已经有空位置?jin),可以d新的观众
            }
            v.check();
            ++count;
        }
    }
    // 观众添加到队列
    void add(viewer v)
    {

        // 同样q用条g变量Q判断队列是否已l满?br />        // 只有在队列尚未满的情况下才向下l?br />        scoped_lock lock(m);
        while(vque.size() >= 15 )
        {
            cond.wait(lock);
        }
        vque.push(v); // 观众添加到队列
        cond.notify_one();  // 通知(g)进E,新的观众q入队列Q这样在size=0时等待的条g可以更新
    }
    int getcount()
    {
        return count;
    }
    int getno()
    {
        return no;
    }
    // {待U程执行完毕q回
    void join()
    {
        t.join();
    }
private:
    thread t;
    mutex m;
    condition cond;
    queue<viewer> vque;
    int count;
    int no;
};

// 一共有10个检口
vector<gate> vgates(10);

// 用随机数模拟观众到达
void arrival()
{   
    default_random_engine re{}; // 产生一个均gؓ(f)31的正态分布的随机?br />    normal_distribution<double> nd(31,8);

    // 随机数引擎和分布绑定一个函数对?br />    auto norm = std::bind(nd, re);
    // 保存随机数的容器
    vector<int> mn(64);
   
    // 产生随机?br />    for(int i = 0;i<700;++i)
        ++mn[round(norm())];
   
    int secs = 100;
    // 产生0?的随机数Q表C众随机地到达某一个检口
    uniform_int_distribution<int>  index{0,9};
     
    // q入(g)口队列
    for(auto i:mn)
    {
        cout<<i<<endl;
        for(auto vi = 1; vi <= i; ++vi)
        {
            // 观众添加到某个gate的队列中
             (vgates[index(re)]).add(viewer());
            // {待一D|?br />            int t = round(secs/(float)(i+1));
            this_thread::sleep(
            posix_time::milliseconds(t));
        }
    }
    // 观众已经全部到达Q进入队?br />     cout<<"finish"<<endl;
    mtx.lock();
    finish = true;
    mtx.unlock();
    //cout<<"unlock"<<endl;
}

int main()
{
    int i = 1;
    // 启动(g)线E?br />    for(gate& g:vgates)
    {
        g.start(i);
        ++i;
    }
    // 启动到达U程Q看看,在C++11中新U程的创建就q么?br />    thread arr = thread(arrival);
    // {待U程l束
    arr.join();
    int total = 0;
    // {待(g)线E结束,q输出处理的人数
    for(gate& g:vgates)
    {
        g.join();
        total += g.getcount();
        cout<<"gate "<<g.getno()
            <<" processed "<<g.getcount()<<" viewers."<<endl;
    }
    cout<<"there are "<<total<<"viewers in total."<<endl;
    return 0;
}
q就是一个线E库的简单应用,模拟?jin)非常复杂的场景?/p> 因ؓ(f)自己对多U程开发还不太熟?zhn)Q这个程序在某些特定条g下会(x)产生?jin)死锁,q有待进一步完?iostream>

]]>
C++品Qweak_ptr与传辑֮的花名册http://www.shnenglu.com/chenlq/archive/2011/09/20/156334.html陈良乔——《我的第一本C++书?/dc:creator>陈良乔——《我的第一本C++书?/author>Tue, 20 Sep 2011 08:29:00 GMThttp://www.shnenglu.com/chenlq/archive/2011/09/20/156334.htmlhttp://www.shnenglu.com/chenlq/comments/156334.htmlhttp://www.shnenglu.com/chenlq/archive/2011/09/20/156334.html#Feedback0http://www.shnenglu.com/chenlq/comments/commentRss/156334.htmlhttp://www.shnenglu.com/chenlq/services/trackbacks/156334.html 原文来自Q?/p> http://imcc.blogbus.com/logs/162618478.html

在C++11中,我们可以使用shared_ptr理某个对象的所有权Q负责对象的析构。然而在某些情况下,我们只是希望安全的访问某个对象,而不x有这个对象的所有权Q对q个的析构负责(有点像电(sh)视剧中的那些不负责Q的男人哦Q只是玩玩而已Q不?x)负责?j)。在q种情况下,我们可以使用表示弱引用的weak_ptr?/p>

weak_ptr可以׃个shared_ptr构徏Q表C个weak_ptr拥有q个shared_ptr所指向的对象的讉K权,注意Q这里仅仅是讉K权,它不?x)改变智能指针的引用计数Q自然也׃?x)去析构q个对象。利用weak_ptrQ我们就可以安全地访问那些不具备所有权的对象?/p>

一个现实中的例子就是学校的传达室,传达室拥有一本学生的名单Q如果某个电(sh)话来?jin)找某个学生Q传辑֮?x)根据花名册d试访问这个学生,如果q个学生q在学校Q就直接呼叫q个学生Q如果已l离开?jin),q给q个学生留一个消息。在q里Q花名册上的学生可能q在学校Q对象还存在Q,也可能已l离开学校Q对象已l析构)(j)Q我们都需要对其进行访问,而weak_ptr是用来讉Kq种不确定是否存在的对象的?/p>

#include <iostream>
#include <map>
#include <algorithm>
#include <memory>
using namespace std;

// 学校的同?br />class human
{
public:
human(string _n):name(_n)
{};
~human()
{
cout<<name<<" was destructed."<<endl;
}
void call() // 嘿,有个?sh)话找?br /> {
cout<<name<<" was called."<<endl;
}
private:
string name;
};
// 传达?br />class doorman
{
public:
doorman(map<string,shared_ptr<human>> humans)
{
// Ҏ(gu)学生对象构造花名册Q注意其中保存的是有shared_ptr构造的weak_ptr
for_each(humans.begin(),humans.end(),
[&names](pair<string,shared_ptr<human>> h)
{
names[h.first] = weak_ptr<human>(h.second);
});
}
// 有个?sh)话打到了(jin)传辑֮?
void call(string name)
{
// 找找看,花名册中有没有这个学?
auto it = names.find(name);
// 如果?
if(it!=names.end())
{
auto man = (*it).second;
// 用lock()函数试获得weak_ptr所指向的shared_ptrQ保存ؓ(f)p
if(auto p = man.lock())
p->call(); // 如果扑ֈ兌的shared_ptrQ也是q个对象q存在,也就是这个学生还在学校,呼叫?br /> else // 如果无法得到兌的shared_ptrQ表C个对象已l不存在?jin),学生d?jin)学校,只能l他留一个消息了(jin)
{
leavemsg(name);
}
}
else // 如果花名册中Ҏ(gu)没有q个名字
{
cout<<name<<" is not in the school."<<endl;
}
}
void leavemsg(string name)
{
cout<<name<<" has left school.I will leave a message for him."<<endl;
}
private:
map<string,weak_ptr<human>> names; // 传达室的花名?br />};
int main()
{
// 学校的学?
map<string,shared_ptr<human>> humans;
humans["Jiawei"] = make_shared<human>("Jiawei");
humans["Chen"] = make_shared<human>("Chen");
humans["Xibei"] = make_shared<human>("Xibei");

// 传达室,Ҏ(gu)学生构造一个花名册
doorman dm(humans);
// 有h找Chen
dm.call("Chen");
// 有h找Fu
dm.call("Fu");

// Chend学校Q对象被析构
humans.erase("Chen");
// 又有人打来电(sh)话找ChenQ这时他已经不在学校Q只能给他留一个消息了(jin)
dm.call("Chen");
// 有h找JiaweiQ她q在学校呢,直接叫她
dm.call("Jiawei");

return 0;
}
从这D늨序的输出Q我们也可以看出Q我们在删除humans容器中的Chenq个元素是,对应的human对象也被析构Qdoorman中指向这个对象的weak_ptrq不影响它的析构Q当我们再次试讉Kq个对象时候,lock()无法成功获得与之兌的shared_ptrQ也无法对其进行访问了(jin)?/map>

Chen was called.
Fu is not in the school.
Chen was destructed.
Chen has left school.I will leave a message for him.
Jiawei was called.
Xibei was destructed.
Jiawei was destructed.

q里大家可能?x)问Qؓ(f)什么不在doorman中用裸指针呢?。。?

那么Qؓ(f)什么不直接使用shared_ptr呢? 参考原文?/map>

ȝhQweak_ptr用于讉K?jin)那些不具备所有权的,可能存在也可能不存在的对象?/map>



]]>
C++品Q吃火锅与shared_ptrQ指针,拯构造函数和deletehttp://www.shnenglu.com/chenlq/archive/2011/09/10/155511.html陈良乔——《我的第一本C++书?/dc:creator>陈良乔——《我的第一本C++书?/author>Sat, 10 Sep 2011 08:10:00 GMThttp://www.shnenglu.com/chenlq/archive/2011/09/10/155511.htmlhttp://www.shnenglu.com/chenlq/comments/155511.htmlhttp://www.shnenglu.com/chenlq/archive/2011/09/10/155511.html#Feedback0http://www.shnenglu.com/chenlq/comments/commentRss/155511.htmlhttp://www.shnenglu.com/chenlq/services/trackbacks/155511.html原文来自

http://imcc.blogbus.com/

C++品Q吃火锅与shared_ptrQ指针,拯构造函数和delete

读者Terry问到一个关于拷贝构造函数的问题Q大家可以参?a >{TerryQ拷贝构造函?/a>Q其中论qC(jin)拯构造函数的必要性,然而,M事物都是h两面性的Q有时候我们需要自己定义类的拷贝构造函数来完成cȝ拯Q然后,有的时候,q种以拷贝一个对象来完成另外一个对象的创徏是不合理的(也就是在现实世界中,q种对象没有可复制性,例如Qh民币Q,是应该被止的。我们来举一个吃火锅的例子:(x)

// 火锅Q可以从中取出其中烫的东?
class hotpot
{
public:
hotpot(string f) : food(f)
{
}
string fetch()
{
return food;
}
private:
string food;
};

// 吃火锅用的碗Q当然是每个Z用的
class bowl
{
public:
bowl(string o) : owner(o)
{
}
void put(string food)
{
cout<<"put "< }

private:
string owner;
};
// 吃火锅的?br />class human
{
public:
// 名子和吃的火?
human(string n,shared_ptr ppot) : name(n),pot(ppot)
{
pbowl = new bowl(name);
};
// OK?jin),从火锅中取出来放到自q里
void fetch()
{
string food = pot->fetch();
// 攑ֈ自己的碗?
coutput(food);
}

private:
string name;
shared_ptr pot;
bowl* pbowl;
};
int main()
{
// 服务员端上来牛肉火锅
shared_ptr fpot(new hotpot("beaf"));
// terry入席
human terry("terry",fpot);
// 又来?jin)一个姓陈的Q这里用的是默认的拷贝构造函数来创徏terry的副?br />human chen = terry;
// terry夹了(jin)一块肉
terry.fetch();
// 陈先生也夹了(jin)一块肉
chen.fetch();

return 0;
}

到这里,g看v来一切OKQ然而从E序输出中我们却发现?jin)问题?x)

terry put beaf into terry's bowl.
terry put beaf into terry's bowl.

O my godQ明明是两个人(terry和chenQ,但是好像却只有一个h做了(jin)两次Q陈先生也把肉加C(jin)terry的碗里?/p>

q就是当cM有指针类型的数据成员Ӟ使用默认的拷贝构造函数所带来的问题,D其中的某些指针成员没有被合理地初始化Q这别是当这些指针指向的是与q个对象QhumanQ有所属关pȝ资源QbowlQ,在这U时候,我们必须自己定义cȝ拯构造函敎ͼ完成指针成员的合理初始化。在human中添加一个拷贝构造函?/p>

human(const human& h)
{
// 两个人显然不能同名,所以只好给个无名氏?
name = "unknown";
// 使用不同的碗
// bowl和human有所属关p,所以这里必d建新的对?
pbowl = new bowl(name);
// 不过可以吃同一个火?
// pot和humanq没有所属关p,所以可以共享一个对?br />pot = h.pot;
};

d拯构造构造函C后,两个Z?x)将东西攑ֈ同一个碗中了(jin)Q自己取得东西不?x)放到别人的里Q?/p>

terry put beaf into terry's bowl.
unknown put beaf into unknown's bowl.

q样修改好多?jin),臛_两个Z?x)用同一个碗?jin)。然而,q样q是有问题,我们无法l第二个人命名,他成?jin)无名氏了(jin),q就是类当中的那些没有可复制性的数据成员Q一个h的名字自然不可以复制l另外一个hQ如果human中有个wifeQ那肯定要上演世界大战了(jin)Q,拯构造函数就?x)生这L(fng)问题?/p>

实际上,对于q类不具备可复制性的对象Qؓ(f)?jin)不引v混ؕQ其拯构造操作是应当被禁止的Q新标准C++11注意到?jin)这个问题,提供了(jin)一个delete关键字来用某些可能存在的(即你规定human不可复制Q也无法LE序员在使用human时写出human chen = terryq样的不合理的代码)(j)默认的(cȝ拯构造函数是默认提供的,对于那些不具备可复制性的cL_(d)q简直是画蛇添Q好?j)办了(jin)坏事情Q不合理的操作,q样Q我们就不能使用拯 构造函C(jin)Q?/p>

// 用human的拷贝构造函?br />human(const human& h) = delete;

l过q样的定义,当我们在代码中尝试将一个对象复制给另外一个对象(?x)调用拷贝构造函敎ͼ(j)Ӟ~译器就?x)出错误提示Q提醒程序员QhiQ这样可不行Q我是独一无二的,不能够被复制

human chen = terry;

~译器给q样的提C:(x)
Noname1.cpp:41:2: error: deleted function 'human::human(const human&)'
Noname1.cpp:59:15: error: used here

所以,ȝhQ在使用拯构造函数时Q有两个需要注意的地方Q?/p>

  • 如果cd中有指向h所属关pȝ对象的指针时Qhuman中的pbowl指向的是属于human的bowl对象Q每个human对象应该有专属的bowl对象Q,我们必须自定义拷贝构造函敎ͼ个指针创建属于自q专属对象?
  • 如果q个cd中,有不具备可复制性的成员Q例如nameQrmbQwife{)(j)Qؓ(f)?jin)防止对象被错误的复Ӟ即我们没有定义拯构造函敎ͼ~译器也?x)默认提供,真是多此一举)(j)Q我们必ȝdelete用拯构造函敎ͼq样才能保证对象不会(x)被错误地复制。关于human的克隆技术,应当是被明o(h)止QdeleteQ的?/li>


]]>
函数调用机制http://www.shnenglu.com/chenlq/archive/2011/07/23/151697.html陈良乔——《我的第一本C++书?/dc:creator>陈良乔——《我的第一本C++书?/author>Sat, 23 Jul 2011 03:27:00 GMThttp://www.shnenglu.com/chenlq/archive/2011/07/23/151697.htmlhttp://www.shnenglu.com/chenlq/comments/151697.htmlhttp://www.shnenglu.com/chenlq/archive/2011/07/23/151697.html#Feedback1http://www.shnenglu.com/chenlq/comments/commentRss/151697.htmlhttp://www.shnenglu.com/chenlq/services/trackbacks/151697.html更多来自Qhttp://imcc.blogbus.com

5.1.2 函数调用机制

在学?fn)编写函C前,我们首先要了(jin)解函数的调用机制Q学?x)如何调用一个已l存在的函数。世界上已经有很多函敎ͼ我们可以直接调用q些函数来完成日怓Q务。世界上已经有很多轮子,我们没有必要再去发明更多同样的轮子,只需要用好它们就可以?jin)。在实际的开发中Q可供调用的现有函数主要有编译器提供的库函数、Windows API?qing)第三方提供的函数库{。通过调用他h的函敎ͼ可以复用他h的开发成果,在其开发成果的基础上,实现快速开发,如图5-3所C?/p>

有了(jin)别h提供的函敎ͼ可以调用这些函数来完成自己的功能。两个函C间的关系是调用与被调用的关系Q我们把调用其他函数的函数称Z调函敎ͼ被其他函数调用的函数UCؓ(f)被调函数。一个函数是主调函数q是被调函数q不是绝对的Q要Ҏ(gu)其所处的相对位置而定Q如果一个函数内部有函数Q则相对其内部的函数它就是主调函敎ͼ如果它的外部有函敎ͼ则相对其外部函数它就是被调函数?/p>

clip_image002

?-3 天上掉下个函数库



]]>
程序装到箱子中Q函数的声明和定?/title><link>http://www.shnenglu.com/chenlq/archive/2011/07/22/151625.html</link><dc:creator>陈良乔——《我的第一本C++书?/dc:creator><author>陈良乔——《我的第一本C++书?/author><pubDate>Fri, 22 Jul 2011 05:25:00 GMT</pubDate><guid>http://www.shnenglu.com/chenlq/archive/2011/07/22/151625.html</guid><wfw:comment>http://www.shnenglu.com/chenlq/comments/151625.html</wfw:comment><comments>http://www.shnenglu.com/chenlq/archive/2011/07/22/151625.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.shnenglu.com/chenlq/comments/commentRss/151625.html</wfw:commentRss><trackback:ping>http://www.shnenglu.com/chenlq/services/trackbacks/151625.html</trackback:ping><description><![CDATA[<p>更多来自Q?a >http://imcc.blogbus.com</a></p> <p> </p> <p>5.1.1 程序装到箱子中Q函数的声明和定?/p> <p>提问Q把大象装到冰箱中需要几步?</p> <p>回答Q需要三步。第一Q打开冰箱Q第二,把大象放q冰;W三Q关上冰?/p> <p>提问Q那么,把一个程序放q箱子需要几步?</p> <p>回答Q需要两步。第一Q声明一个函敎ͼW二Q定义这个函数?/p> <p>没错Q把一个函数放q箱子比把大象放q冰p要简单。当分析一D长的程序代码时Q往往?x)发C些代码所实现的功能相Ҏ(gu)较独立。我们将E序中这些相Ҏ(gu)较独立的功能代码l织CP用函数对其进行封装,也就是将一个较长的E序分放到各个函数箱子中?/p> <p>要装东西Q先得准备好子。ؓ(f)?jin)找到具体功能实C码的子Q需要给子贴上标签Q这个标{ְ是函数的声明Q如?-2所C?/p> <p> <a > <img style="border: 0px currentColor; padding-top: 0px; padding-right: 0px; padding-left: 0px; display: inline; background-image: none;" title="clip_image002" alt="clip_image002" src="http://images.cnblogs.com/cnblogs_com/chenliangqiao/201107/201107221323004430.gif" border="0" height="232" width="246" /> </a> </p> <p>?-2 声明一个函敎ͼ为箱子脓(chung)?/p><img src ="http://www.shnenglu.com/chenlq/aggbug/151625.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.shnenglu.com/chenlq/" target="_blank">陈良乔——《我的第一本C++书?/a> 2011-07-22 13:25 <a href="http://www.shnenglu.com/chenlq/archive/2011/07/22/151625.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>把程序装q箱子:(x)用函数封装程序功?/title><link>http://www.shnenglu.com/chenlq/archive/2011/07/21/151526.html</link><dc:creator>陈良乔——《我的第一本C++书?/dc:creator><author>陈良乔——《我的第一本C++书?/author><pubDate>Thu, 21 Jul 2011 01:45:00 GMT</pubDate><guid>http://www.shnenglu.com/chenlq/archive/2011/07/21/151526.html</guid><wfw:comment>http://www.shnenglu.com/chenlq/comments/151526.html</wfw:comment><comments>http://www.shnenglu.com/chenlq/archive/2011/07/21/151526.html#Feedback</comments><slash:comments>2</slash:comments><wfw:commentRss>http://www.shnenglu.com/chenlq/comments/commentRss/151526.html</wfw:commentRss><trackback:ping>http://www.shnenglu.com/chenlq/services/trackbacks/151526.html</trackback:ping><description><![CDATA[<p>更多来自Q?a >http://imcc.blogbus.com</a></p> <p> </p> <p>t 把程序装q箱子:(x)用函数封装程序功?a ><img style="margin: 0px; border: 0px currentColor; padding-top: 0px; padding-right: 0px; padding-left: 0px; display: inline; background-image: none;" title="clip_image001" alt="clip_image001" src="http://images.cnblogs.com/cnblogs_com/chenliangqiao/201107/20110721094157102.gif" border="0" height="2" width="600" /></a></p> <p>在完成豪华的工资l计E序之后Q我们信?j)倍增Q开始向C++世界的更p处探索?/p> <p>现在Q可以用各U数据类型和E序程控制l构来编写完整的E序?jin)。但是,随着要处理的问题来复杂,E序的代码也来复杂,dC来长?jin)。这像我们所有东襉K堆放C个仓库中Q随着东西来多Q仓库慢慢就被各U东西堆满了(jin)Q显得杂乱无章,理h非常困难。面对一个杂乱无章的仓库Q聪明的仓库理员提供了(jin)一个很好的理办法Q将东西分门别类地装q箱子,然后有序地堆攑֐个箱子?/p> <p>q个好方法也可以用到E序设计中,把程序装q箱子,让整个程序结构清晰?/p> <p> <a > <img style="margin: 0px; border: 0px currentColor; padding-top: 0px; padding-right: 0px; padding-left: 0px; display: inline; background-image: none;" title="clip_image003" alt="clip_image003" src="http://images.cnblogs.com/cnblogs_com/chenliangqiao/201107/201107210941599032.gif" border="0" height="432" width="432" /> </a> </p> <p>5.1 函数是一个大子</p> <p>当要处理的问题越来越复杂Q程序越来越庞大的时候,如果把这些程序代码都攑ֈdCQ将使得整个d数异常臃肿,q样?x)给E序的维护带来麻?ch)。同Ӟ要让一个主函数来完成所有的事情Q几乎是一个不可能完成的Q务。在q种情况下,可以Ҏ(gu)“分而治之”的原则Q按照功能的不同大的程序进行模块划分,h相同功能的划分到同一个模块中Q然后分别处理各个模块。函敎ͼ则成为模块划分的基本单位Q是对一个小型问题处理过E的一U抽象。这像理一个仓库,L同cȝ东西攑ֈ同一个箱子中Q然后通过理q些子来管理整个仓库。在具体的开发实践中Q我们先相对独立的、经怋用的功能抽象为函敎ͼ然后通过q些函数的组合来完成一个比较大的功能。D一个简单的例子Q看书看得肚子饿?jin),我们要?chng)方便面吃。这其实是一个很复杂的过E,因ؓ(f)q一q程中我们先要洗锅,然后烧水Q水烧开后再泡面Q吃完面后还要洗。如果把整个q程描述在主函数中,那么dC(x)非常复杂Q结构؜乱。这时就可以使用函数来封装整个过E中的一些小步骤Q让整个d数简化ؓ(f)对这些函数的调用Q如?-1所C?/p> <p> <a > <img style="border: 0px currentColor; padding-top: 0px; padding-right: 0px; padding-left: 0px; display: inline; background-image: none;" title="clip_image005" alt="clip_image005" src="http://images.cnblogs.com/cnblogs_com/chenliangqiao/201107/201107210942005835.gif" border="0" height="202" width="401" /> </a> </p> <p>?-1 程序封装到子Q分而治?/p><img src ="http://www.shnenglu.com/chenlq/aggbug/151526.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.shnenglu.com/chenlq/" target="_blank">陈良乔——《我的第一本C++书?/a> 2011-07-21 09:45 <a href="http://www.shnenglu.com/chenlq/archive/2011/07/21/151526.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>对@环进行控Ӟ(x)break与continuehttp://www.shnenglu.com/chenlq/archive/2011/07/20/151464.html陈良乔——《我的第一本C++书?/dc:creator>陈良乔——《我的第一本C++书?/author>Wed, 20 Jul 2011 03:48:00 GMThttp://www.shnenglu.com/chenlq/archive/2011/07/20/151464.htmlhttp://www.shnenglu.com/chenlq/comments/151464.htmlhttp://www.shnenglu.com/chenlq/archive/2011/07/20/151464.html#Feedback0http://www.shnenglu.com/chenlq/comments/commentRss/151464.htmlhttp://www.shnenglu.com/chenlq/services/trackbacks/151464.htmlhttp://imcc.blogbus.com

4.3.4 对@环进行控Ӟ(x)break与continue

// 大款的收支统计程?/p>

int nTotal = 0;

int nInput = 0;

do

{

cout<< "误入你的收入或支出Q?;

cin>>nInput;

if( 1000< nInput ) // 毛毛雨啊Q就不用l计?/p>

continue;

nTotal += nInput;

}while( 0 != nInput );

在这个大Ƅ收支l计E序中,nInput接收用户输入后判断其值是否小? 000Q如果小? 000Q则执行continue关键字,跌后面的加和语句“nTotal += nInput;”,而直接蟩转到Ҏ(gu)件表辑ּ? != nInput”的计算Q判断是否可以开始下一ơ@环。值得注意的是Q在for循环中,执行continue后,控制条g变化的更改语句ƈ没有被蟩q,仍然被执行Q然后再计算条g表达式,试下一ơ@环?/p>

虽然break和continue都是在某U条件下跛_循环Q但是两者有本质的差别:(x)break是蟩出整个@环,立刻l束循环语句的执行;而continue只蟩出本ơ@环,l箋执行下一ơ@环。图4-6展示?jin)break和continue之间的区别?/p>

clip_image002[4]

?-6 break和continue之间的区?/p>

]]>
《我的第一本C++书》迷你书——看囑֭C++免费下蝲http://www.shnenglu.com/chenlq/archive/2011/07/19/151370.html陈良乔——《我的第一本C++书?/dc:creator>陈良乔——《我的第一本C++书?/author>Tue, 19 Jul 2011 03:41:00 GMThttp://www.shnenglu.com/chenlq/archive/2011/07/19/151370.htmlhttp://www.shnenglu.com/chenlq/comments/151370.htmlhttp://www.shnenglu.com/chenlq/archive/2011/07/19/151370.html#Feedback1http://www.shnenglu.com/chenlq/comments/commentRss/151370.htmlhttp://www.shnenglu.com/chenlq/services/trackbacks/151370.html clip_image002

The world is built on C++.

—?/em> Herb Sutter

看得有趣、学得轻?/p>

看图也能学C++Q!

没错Q看图也能学C++Q?/p>

q本q你书是《我的第一本C++书》的q你版,它抽取了(jin)《我的第一本C++书》中的全部的_插图Qƈ配上相应的解释说明。它以图文ƈ茂的生动形式Q向你讲解那些所谓的高深的C++知识Q让你对那些抽象的C++知识有一个更加Ş象的理解Q向你展C个美丽而神U的C++世界Q让你在有趣的看图过E中Q轻村֜学到?jin)C++知识?/p>

clip_image004

看得有趣、学得轻?

免费下蝲



]]>
þ99ۺϾƷ| þþþþùƷ | ޾ƷþþþþĻ | պһþþþþ| þþžžƷ99Ʒ| ھƷþۺ88| Ůͬþ| պľþ| ޹ƷþþþþԻ| þþƷ۲ӰԺ| ƷþþþþþҹƬ| þþƷѹۿ| 97þþƷˬ| ƷþþþþþþþĻ | Ʒþþ99| Ʒþˬۺ| Ʒݾþþþø99| þþƷ99Ӱ| þù׾Ʒǿ| þù㽶Ƶ| ޾Ʒþþþþò| þþƷһۺ| ݾƷŮ˾þþþþ| þ㽶߿ۿ| þþƷ| ˾þۺ| þһѲ| ŷպƷþ| avttþþƷ| ھƷþþþþþ| ޾Ʒ˾þþ| þþþƷsmվ | ޹þþۺ| þùֱ| ŷպþĻ| 99ŷþþþƷѿ| ˾Ʒһþ| ޾Ʒþþþϼ| þоƷƵ| þùҹƵ| þþƷ |