场景二:在一个类向另一个类发送消息

场景二:在一个类向另一个类发送消息

假设有一个 recv1 类,使用 recv1 实例化了 10000 个对象(在 main 函数中实例化),现有 sender 类,要在 sender 对象中发送消息给这 10000 个对象。

mgnotify 消息库

使用 mgnotify 消息库,只需要将发送消息类在 sender 中实例化并发送即可,主打的就是随时随地可以随心所欲的发送消息。

mmv 用例源码

关键代码:

// 1. 定义消息
class carrier : public BaseMessage<carrier>
{
public:
    string name;
    // 测试耗时: 开始时间
    chpt start_time;
};

// 2. 定义消息接收类
class recv1 : public BaseHandle<carrier>
{
public:
    recv1() : _id(-1) {}
    ~recv1() {}
    void setId(int id) { _id = id; }
    virtual bool handle(const carrier* msg) override;
private:
    int _id;
};

// 3. 类消息处理
bool recv1::handle(const carrier* msg)
{
    auto end = high_resolution_clock::now();
    std::chrono::duration<double, std::milli> elapsed = end - msg->start_time;
    cout << "recv1--> id: " << _id << " name: " << msg->name << ", 从开始发送消息到接受消息耗时: " << elapsed.count() << " ms." << endl;

    return true;
}

// 4. sender 类中发送消息
class sender
{
public:
    sender() {}
    ~sender() {}
    void send() {
        carrier m1;
        m1.start_time = high_resolution_clock::now();
        m1.name = "ljj";
        // 发送同步消息(如果是异步消息,可能消息还没有接收完整,进程已经结束)
        m1.send();
    }
};

// 5. 构建对象并发送消息
int main()
{
    list<recv1*> rs1;
    auto start = high_resolution_clock::now();
    int count = 10000;
    cout << count << "个接收者构建中,请稍后...\n";
    for(int i = 0; i < count; i++) {
        recv1 *r1 = new recv1;
        r1->setId(i);
        rs1.push_back(r1);
    }
    auto end = high_resolution_clock::now();
    std::chrono::duration<double, std::milli> elapsed = end - start;
    cout << "attach " << count << " 接收者耗时:" << elapsed.count() << " ms." << endl;

    start = high_resolution_clock::now();
    while (!rs1.empty()) {
        auto t = rs1.back();
        rs1.pop_back();
        delete t;
        t = nullptr;
    }
    end = high_resolution_clock::now();
    elapsed = end - start;
    cout << "detach " << count << " 接收者耗时:" << elapsed.count() << " ms." << endl;
    
    return 0;
}

总结

怎么样?这时候优势就体现出来了吧,而且这还是比较简单的情况,如果是更加复杂的情况,比如 sender 类中包含其他的类对象或者多个对象,在子对象中发送消息呢?又比如有更复杂的继承关系呢?

<think>我们正在讨论Java中对象之间如何访问彼此的属性。根据引用[2]中关于Java、对象和方法的格式描述,以及引用[4]中对象之间通过消息发送进行交互的描述,我们可以这样理解: 在Java中,一个对象要访问一个对象的属性,主要取决于属性的访问修饰符(public, protected, private)以及两个对象之间的关系(如是否在同一个中、是否在同一个包中、是否有继承关系等)。 具体规则如下: 1. **public属性**:任何对象都可以直接访问。 2. **protected属性**:同一个包中的可以访问,不同包中的子也可以访问(通过继承)。 3. **默认(包私有)属性**:同一个包中的可以访问。 4. **private属性**:只有同一个内部的方法可以访问。 因此,如果一个对象的属性是public的,那么一个对象可以直接通过点运算符(.)访问。但是,通常我们不推荐将属性直接暴露为public,因为这破坏了封装性。更常见的做法是使用private属性,并提供public的getter和setter方法。 例如,引用[3]中的Person有私有属性name和address,它提供了Getter和Setter方法,这样其他对象就可以通过这些方法来访问和修改属性。 下面是一个简单的例子: ```java public class Person { private String name; // 私有属性 // 公共的getter方法 public String getName() { return this.name; } // 公共的setter方法 public void setName(String name) { this.name = name; } } public class Main { public static void main(String[] args) { Person person1 = new Person(); person1.setName("Alice"); Person person2 = new Person(); // 通过getter方法访问person1的name属性 System.out.println(person1.getName()); // 输出: Alice } } ``` 在上面的例子中,person2并没有直接访问person1的私有属性,而是通过person1提供的公共方法getName()来获取name的值。 外,如果两个对象在同一个中,那么即使属性是private,它们也可以互相访问。因为private属性在同一个内部是可见的。例如: ```java public class Person { private String name; public void copyNameFrom(Person other) { this.name = other.name; // 在同一个中,可以直接访问一个对象的私有属性 } } ``` 但是,这种情况仅限于同一个内部。不同的对象之间,只能通过公共方法(如getter)来访问私有属性。 总结: - 在Java中,一个对象可以访问一个对象的属性,但必须遵循访问修饰符的规则。 - 通常,我们通过提供公共的getter和setter方法来控制对私有属性的访问,以保证封装性。 §§相关问题§§ 1. Java中访问修饰符有哪些?它们分别有什么作用? 2. 如何正确使用getter和setter方法来封装属性? 3. 在同一个中,为什么可以访问一个对象的私有属性? 4. 如何在不同包中的之间访问属性? 5. Java中封装性的重要性体现在哪些方面?</think>### Java中对象访问彼此属性的机制 在Java中,**一个的对象可以访问一个对象的属性**,但必须遵循严格的封装规则和访问控制机制。核心取决于属性的访问修饰符(`public`, `protected`, `private`)以及之间的关系。以下是详细说明: --- ### 一、访问规则(基于访问修饰符) 1. **`public` 属性(直接访问)** 任何对象可直接访问: ```java class Person { public String name; // public属性 } public class Main { public static void main(String[] args) { Person person1 = new Person(); person1.name = "Alice"; Person person2 = new Person(); person2.name = person1.name; // 直接访问一个对象的属性 System.out.println(person2.name); // 输出: Alice [^2] } } ``` 2. **`private` 属性(通过Getter/Setter间接访问)** 必须通过提供的公共方法访问: ```java class Person { private String name; // private属性 // Getter方法 public String getName() { return this.name; } // Setter方法 public void setName(String name) { this.name = name; } } public class Main { public static void main(String[] args) { Person person1 = new Person(); person1.setName("Alice"); Person person2 = new Person(); person2.setName(person1.getName()); // 通过Getter访问一个对象的属性 System.out.println(person2.getName()); // 输出: Alice [^2][^5] } } ``` 3. **`protected` 属性(继承关系中访问)** 子对象可访问父对象的`protected`属性: ```java class Animal { protected String type; // protected属性 } class Dog extends Animal { // 继承关系 public void setType(Animal animal) { this.type = animal.type; // 子访问父对象的属性 } } ``` --- ### 、特殊场景与注意事项 1. **静态属性(属性)的访问** 通过名直接访问,无需对象实例: ```java class Config { public static String env = "production"; // 静态属性 } public class Main { public static void main(String[] args) { System.out.println(Config.env); // 直接通过名访问 } } ``` 2. **对象作为方法参数传递** 通过方法参数访问一个对象的属性: ```java class Calculator { public int add(Person p1, Person p2) { return p1.getAge() + p2.getAge(); // 访问传入对象的属性 [^4] } } ``` 3. **浅拷贝时的属性访问** 克隆对象可直接访问原对象的引用型属性(共享内存地址): ```java Person person1 = new Person("Alice", new Address("New York")); Person person2 = (Person) person1.clone(); // 浅拷贝 System.out.println(person1.getAddress() == person2.getAddress()); // 输出: true [^3] ``` --- ### 三、封装的重要性与最佳实践 - **封装原则**:Java强烈推荐将属性设为`private`,通过Getter/Setter控制访问,避免数据被意外修改[^2][^5]。 - **访问控制总结**: | 修饰符 | 同 | 同包 | 子 | 其他包 | |------------|------|------|------|--------| | `private` | ✓ | ✗ | ✗ | ✗ | | `protected`| ✓ | ✓ | ✓ | ✗ | | `public` | ✓ | ✓ | ✓ | ✓ | > ⚠️ 直接访问`public`属性虽可行,但会破坏封装性。生产代码中应优先使用Getter/Setter[^5]。 --- ### 四、总结 - **对象可直接访问**:一个对象的`public`属性(不推荐)。 - **对象需间接访问**:通过Getter/Setter访问`private`或`protected`属性(推荐)。 - **可直接访问**:静态属性(`static`修饰)。 通过访问修饰符和封装机制,Java在灵活性和数据安全之间取得了平衡[^2][^4][^5]。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

ALONE_WORK

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值