18. Mouse 鼠标、KeyBoard 键盘和 Action 消息事件处理

news2025/1/9 16:36:33

在本节的例子中,会自定义很多UI控件实现不同的事件响应,如下图所示:
在这里插入图片描述

IOKit 事件框架

事件流程

OS X的事件依赖 IOKit 框架,事件发生后首先会传递到IOKit框架中处理,然后通知Window Server服务层处理,由Window Server存储到到一个FIFO队列中,再逐一转发到当前的Active Window或Active App中进行处理;
在这里插入图片描述

  • 每个应用都有一个 Main Run Loop,它会一直遍历系统的 FIFO Event Queue队列,如果有属于自己的事件,则会通过NSApp的senEvent()方法转发给NSWindow,再经NSWindow转发给NSView的合适对象去处理;
  • 所有继承了NSView的控件都可以响应事件,其它的还有NSApplication、NSWindow、NSDrawer、NSWindowController也可以响应事件;

First Responsers

First Responders称为事件的第一响应者;AppKit中的事件都处于一个响应的链条中,这个链条是由一个叫做NSResponder 的类定义。这个响应链条其实是一个列表,它里面装满了能够响应用户事件的对象,当用户点击鼠标,或者按下键盘的某个键,或者触摸触控板都会生成Event事件,然后在响应链条中寻找可以处理这个事件的对象对事件进行处理。一个对象如果可以处理事件,那么这个对象必须继承自NSResponder这个类。

一个NSResponder实例对象有三个组件:事件消息(鼠标,键盘,触控板等产生的)、动作消息(比如NSButton 执行target 的action 方法,就属于一种action消息)、响应链条。

事件拦截

此功能相当于web开发中的拦截器一样,真实开发中不太常用,多数用于调试使用。

import Cocoa

class Window: NSWindow {
    
    override func sendEvent(_ event: NSEvent) {
        NSLog("sendEvent \(event)")
        //对event做统计处理,内部转发处理
        super.sendEvent(event)
    }
    
    override func postEvent(_ event: NSEvent, atStart flag: Bool) {
         NSLog("sendEvent \(event)")
         super.postEvent(event,atStart:flag)
    }
}
  • sendEvent():可以拦截到所有的事件消息,在这里可以统一转发或特殊处理;
  • postEvent():分发事件;

事件监控

先在ViewController中添加事件监听器,以便后面观察,,真实开发中不太常用,多数用于调试使用,可定义两类事件:

  • startGlobalEventMoniter():全局事件,即监听鼠标和键盘的所有事件;
  • startLocalEventMoniter():局部事件,只监听当前应用上发生的事件;

监控器添加

import Cocoa

class ViewController: NSViewController {

    //定义事件类型:全局和局部,局部是指在控件上操作
    var gEventHandler: Any?
    var lEventHandler: Any?
    
    override func viewDidLoad() {
        super.viewDidLoad()

        //全局事件监听
        self.startGlobalEventMoniter()
        //局部事件监听
        self.startLocalEventMoniter()
        
        self.view.window?.makeFirstResponder(self)
    }
    
    override var representedObject: Any? {
        didSet {
        // Update the view, if already loaded.
        }
    }
    
    func startGlobalEventMoniter() {
        self.gEventHandler = NSEvent.addGlobalMonitorForEvents(
            matching: [NSEvent.EventTypeMask.keyDown,NSEvent.EventTypeMask.leftMouseDown],
            handler: {
                event in print("全局事件: \(event)")
            }
        )
    }
    
    func startLocalEventMoniter() {
        self.lEventHandler = NSEvent.addLocalMonitorForEvents(
            matching: [NSEvent.EventTypeMask.keyDown,NSEvent.EventTypeMask.leftMouseDown],
            handler: {
                event in print("控件事件 \(event)")
                return event
          }
        )
    }
    
   	// func stopEventMoniter() {
    //    NSEvent.removeMonitor(self.gEventHandler!)
    //    NSEvent.removeMonitor(self.lEventHandler!)
    //}

}

监控器删除

在窗口或页面关闭时删除监控,需要手工调用一下,这个方法可在NSWindow中调用。

    func stopEventMoniter() {
        NSEvent.removeMonitor(self.gEventHandler!)
        NSEvent.removeMonitor(self.lEventHandler!)
    }

事件分发(Event Dispatch)

在主事件循环中(main event runloop),应用程序对象(NSApp)会不断的从事件队列中(event queue)获取最前面的事件,然后将它转换为NSEvent 对象后,派发到最终目标.

  • NSApp是通过nextEventMatchingMask:untilDate:inMode:dequeue:这个方法从事件队列中获取到事件,当事件队列为空的时候(也就是队列中无事件),这个方法会阻塞,直到有新的事件到来才会继续.
  • NSApp将事件转换为NSEvent后,第一件事就是调用sendEvent:方法进行派发.
  • 大部分的情况下,NSApp都会将事件派发给用户操作的那个窗口(NSWindow),这是通过调用窗口(NSWindow)的sendEvent:方法完成的.
  • NSWindow窗口对象将事件以NSResponder Message消息的形式(比如mouseDown:或者keyDown:)派发到与用户操作关联的NSView对象.
  • NSWindow派发事件时会根据事件类型略有不同:对于鼠标和触控板事件,NSWindow对象会将事件派发到用户鼠标点击的NSView.对于键盘(keyboard)事件,NSWindow通常会将事件派发给key Window第一响应者

由此可见,在事件派发的过程中,会根据事件种类(AppKit中定义的NSAppKitDefined类型)的不同而进行不同的派发选择.有些事件只能由NSWindow或者NSApplication自身来处理,比如应用的隐藏/显示/激活状态/失去激活状态等。

其他事件派发

在应用程序中,我们可以使用NSTrackingArea类添加一个监控区域,这些事件NSWindow对象会直接派发到拥有这个区域的指定对象(通常发送 mouseEntered:和 mouseExited:消息).

应用程序(NSApplication)生成的周期性事件(NSPeriodic)通常不会使用sendEvent:派发,它们是通过某个NSObject对象注册后(通过调用nextEventMatchingMask:untilDate:inMode:dequeue: 方法)才会得到处理.具体的详细内容,可以参考Other Types of Events

NSEvent对象

下列数据为Event的输出:

NSEvent: 
	type=LMouseDown  # 事件类型,此为鼠标左键点击
	loc=(1538.98,531.011)  # 鼠标当前点击的屏幕位置,屏幕原点为左上角
	time=73377.2 
	flags=0 
	win=0x0 
	winNum=79 
	ctxt=0x0 
	evNum=15613 
	click=1  # 鼠标点击次数,如果是双击则此值为2
	buttonNumber=0 
	pressure=1 
	deviceID:0x40000004be0f1e7 
	subtype=NSEventSubtypeTouch

Mouse 鼠标事件

鼠标事件主要分为点击、 拖放两类,同时需要区域跟踪以及鼠标位置这两方面数据的支撑,如果需要处理鼠标坐标,一般还要转换成视图坐标再处理

鼠标事件绑定

鼠标事件属于控件代理中的抽象方法,只需要覆盖实现即可。

    //定义在相应的ViewController中
    override func mouseDown(with event: NSEvent) {
        print("mouseDown left \(event)")
    }
  • mouseDown:左键按下
  • rightMouseDown:右键按下
  • mouseUp:左键松开
  • rightMouseUp:右键松开

判断特殊键

判断点击鼠标时,是否同是按下了特殊键:

  //如果同时按下了command键
   if event.modifierFlags.contains(NSEvent.ModifierFlags.command) {
       self.wantsLayer = true
       self.layer?.borderColor = NSColor.gray.cgColor
       self.layer?.borderWidth = 10
   }

判断鼠标双击

判断Event事件参数

        //判定是否鼠标双击事件
        if event.clickCount>=2 {
            NSLog("mouse  double click event ")
        }
        else {
            super.mouseDown(with: event)
        }

实现鼠标拖放事件

鼠标拖放是一个连续的事件,按mouseDown -> mouseDragged -> mouseUp这样顺序执行,这也是拖放功能的核心实现。

class DragView: NSView {

    var dragged: Bool = false
    var centerBox: NSRect?
    
    override  func awakeFromNib() {
        super.awakeFromNib()
        centerBox = self.bounds.insetBy(dx: 10,dy: 10);
    }
    
    override func draw(_ dirtyRect: NSRect) {
        super.draw(dirtyRect)
        
        if(dragged){
            NSColor.blue.setFill()
        }
        else {
            NSColor.green.setFill()
        }
        dirtyRect.fill()
    }
    
    override func mouseDown(with event: NSEvent) {
        //获取鼠标点击位置坐标
        let eventLocation = event.locationInWindow
        //转化成视图的本地坐标
        let pointInView    = self.convert(eventLocation, from: nil)
        //判断当前鼠标位置是否在中心点附近范围内
        if NSPointInRect(pointInView, centerBox!) {
            dragged = true
        }
    }
    
    override func mouseDragged(with event: NSEvent) {
        if dragged {
            let eventLocation = event.locationInWindow
            let positionBox = NSRect(x: eventLocation.x, y: eventLocation.y, width: self.frame.size.width, height: self.frame.size.height)
            //更新视图位置
            self.frame = positionBox
            //重绘界面
            self.needsDisplay = true
        }
    }
    
    override func mouseUp(with event: NSEvent) {
        dragged = false
        self.needsDisplay = true
    }
    //鼠标指针形状
    override func cursorUpdate(with event: NSEvent) {
        NSCursor.crosshair.set()
    }
}

实现鼠标事件跟踪

出于对性能的考虑,一般拖放时需要设置一个可拖放的监控区域,只有鼠标进入到此区域时才可以触发拖动,所以设计一个鼠标的监控区域的示例代码如下,完整上述不完整的拖放代码。

class TrackView: NSView {

    var tracking: Bool = false
    
    override func awakeFromNib() {
        super.awakeFromNib()

        //监控区域
        let eyeBox = CGRect(x: 0, y: 0, width: 80, height: 80)
        let trackingArea = NSTrackingArea(rect: eyeBox, options: [NSTrackingArea.Options.mouseMoved,NSTrackingArea.Options.mouseEnteredAndExited,NSTrackingArea.Options.activeInKeyWindow,NSTrackingArea.Options.cursorUpdate ], owner: self, userInfo: nil)
        self.addTrackingArea(trackingArea)
    }
    
    override func draw(_ dirtyRect: NSRect) {
        super.draw(dirtyRect)
        if(tracking){
            self.wantsLayer = true
            self.layer?.borderWidth = 10
            self.layer?.borderColor = NSColor.red.cgColor
        }
        else {
            self.wantsLayer = true
            self.layer?.borderWidth = 1
            self.layer?.borderColor = NSColor.gray.cgColor
        }
    }
    
    //进入区域
    override func mouseEntered(with event: NSEvent) {
        tracking = true
        self.needsDisplay = true
    }
    
    override func mouseMoved(with event: NSEvent) {
        
        
    }
    //离开区域
    override func mouseExited(with event: NSEvent) {
        tracking = false
        self.needsDisplay = true
    }
    
    //鼠标光标更新为十字架形状
    override func cursorUpdate(with event: NSEvent) {
       NSCursor.crosshair.set()
    }
    //快捷键,
    override func performKeyEquivalent(with event: NSEvent) -> Bool {
        let characters = event.characters
        if characters == "i" {
            NSApp.terminate(self)
            return true
        }
        return false
    }
}

以上差不多就是鼠标事件的基本内容。

Keyboard 键盘事件

键盘事件,比较复杂,除了普通键外,还有特殊键,快捷键,控制键等,如果是:

  • 快捷键:NSApp会转发事件到相应NSWindow的控件或菜单,执行相应的操作;
  • 控制键:转到到keyWindow,同不同的控件负责事件的响应;
  • 普通键:由使用sendEvent()转发到keyWindow的First Responders对象视图,如果视图是文本类型,是执行insertText()方法,在文本控件中显示;

快捷键

快捷键,默认为 command+key 组合,其中command为快捷键,下面代码是快捷键的判断,判断是否同时按下了command+j,也可用普通的keyDown实现。

class PerformKeyButton: NSButton {
    
    override func performKeyEquivalent(with event: NSEvent) -> Bool {
        let characters = event.characters
        if characters == "j" {
            NSApp.terminate(self)
            return true
        }
        return false
    }
}

控制键

控制键包括:Tab、Shift、Space、Arrow、Option等,这些键用来在当前活动的Window内切换选择不同的控件或者模拟执行鼠标按下时的操作。

class KeyImageView: NSImageView {
    
    override func keyDown(with event: NSEvent) {
        NSLog("keyDown \(event.characters) modifierFlags = \(event.modifierFlags)")
        //单个功能键按下判断
        if event.modifierFlags.contains(NSEvent.ModifierFlags.command) {
            NSLog("modifierFlags command")
        }
        
        if event.modifierFlags.contains(NSEvent.ModifierFlags.shift) {
            NSLog("modifierFlags shift")
        }
        
        if event.modifierFlags.contains(NSEvent.ModifierFlags.control) {
            NSLog("modifierFlags shift")
        }
        
        //组合按键判断,是否同时按下
        if event.modifierFlags.contains(NSEvent.ModifierFlags.command) &&  event.modifierFlags.contains(NSEvent.ModifierFlags.shift) {
            
        }
        
        //回车
        if event.keyCode == 36 {
            NSLog("return key pressed!")
        }
        //空格
        if event.keyCode == 49 {
            NSLog("space key pressed!")
        }
        //上箭头
        if event.keyCode == 126 {
            NSLog("Up Arrow key pressed!")
        }
        //下箭头
        if event.keyCode == 125 {
            NSLog("Down Arrow key pressed!")
        }
        //左箭头
        if event.keyCode == 123 {
            NSLog("Left Arrow key pressed!")
        }
        //右箭头
        if event.keyCode == 124 {
            NSLog("Right Arrow  key pressed!")
        }
        
        super.keyDown(with: event)
    }
}

在Mac OS操作系统中默认提供了一些组合键,这些可以直接使用。也可以修改成自定义的组合键,配置文件存放在下边的路径中,注:不同版本的 OS X 路径不太一样,查下官方文档即可:
/System/Library/Frameworks/AppKit.framework/Versions/C/Resources/StandardKeyBinding.dict

文字输入

文字输入理论上只对TextField和Text View这两个控件有作用,文本输入分两种情况:

  • 特殊键:比如delete, enter等由doCommandBySelector分发到对应的事件处理;
  • 普通键:统一由insertText处理;
//要监控输入事件,首先打开开关
    override var acceptsFirstResponder: Bool {
        return true
    }

普通键

普通的文本事件会触发keyDown()方法,在其内部会经过一个解析过程interpreteKeyEvents(),最后显示在相应的控件中。

    override func keyDown(with event: NSEvent) {
        self.interpretKeyEvents([event])
    }

特殊键

对于特殊键,需要在doCommand()方法中做综合判断特殊处理(也可以复写特定的子方法,下面第二个例子中代码)。

class TextView: NSTextView {

//    override func doCommand(by selector: Selector) {
//        回车键
//        if selector == #selector(NSResponder.insertNewline(_:)) {
//            NSLog("insertNewline")
//        }
//    }
    
    
    override var acceptsFirstResponder: Bool {
        return true
    }
}

下面代码是模拟的一个文本输入框

class CustomTextView: NSView {

    var string:NSMutableString =  NSMutableString()
    override func draw(_ dirtyRect: NSRect) {
        super.draw(dirtyRect)
        self.wantsLayer = true
        self.layer?.borderWidth = 1
        self.layer?.borderColor = NSColor.gray.cgColor
        
        if string.length > 0 {
           string.draw(in: dirtyRect, withAttributes: [:])
        }
    }
    
    override func keyDown(with event: NSEvent) {
        self.interpretKeyEvents([event])
    }
    
    override func insertText(_ insertString: Any) {
        string.append(insertString as! String)
        NSLog("insertString \(string)");
        self.needsDisplay = true
    }
    
    
    override func moveUp(_ sender: Any?) {
        NSLog("moveUp")
    }
    override func moveDown(_ sender: Any?) {
        NSLog("moveDown")
    }
    override func moveLeft(_ sender: Any?) {
        NSLog("moveLeft")
    }
    override func moveRight(_ sender: Any?) {
        NSLog("moveRight")
    }
    
    override func insertNewline(_ sender: Any?) {
        NSLog("insertNewline")
    }
    override func deleteBackward(_ sender: Any?) {
        NSLog("deleteBackward")
    }
    
    
    override var acceptsFirstResponder: Bool {
        return true
    }
    
    //    override var canBecomeKeyView: Bool {
    //        return false
    //    }
    //
    //    override var acceptsFirstResponder: Bool {
    //        return true
    //    }
    //
    //
    //    override func becomeFirstResponder() -> Bool {
    //
    //        return true
    //    }
    //
    //    override func resignFirstResponder() -> Bool {
    //        return true
    //    }
    
}

Action 消息事件

普通的事件在控件内部处理,比如keyDown这类事件。而Action消息事件处理一般是在target内部定义的,如NSControl, NSMenu等控件都是以Action消息形式响应事件的。

Action 消息是一种特殊的系统事件,它是通过NSapp的sendAction()方法转发的,此方法有两个重要参数:

  • action(sel):事件响应方法,类型为SEL对象;
  • target(id):事件关联的对象,比如controller或其它;
  • sender(id):事件发出者对象,一般是当前的控件;

在ViewController中处理事件

ViewController继承了NSResponser,对于普通事件可以直接处理,而复杂消息则需要先调用window.makeFirstResponder()成为第一事件响应者才能再处理。

比如在ViewController扩展以下内容:

extension ViewController: NSTextFieldDelegate,NSTextViewDelegate {
    
     //MARK: NSTextFieldDelegate
    
     func control(_ control: NSControl, textView: NSTextView, doCommandBy commandSelector: Selector) -> Bool {
        if commandSelector == #selector(NSResponder.insertNewline(_:)) {
            NSLog("textField Enter key pressed!")
            return true
        }
        if commandSelector == #selector(NSResponder.deleteBackward(_:)) {
            NSLog("textField delete key pressed!")
            return true
        }
        
        return false
    }
    
    
    //MARK: NSTextViewDelegate
    
    func textView(_ textView: NSTextView, doCommandBy commandSelector: Selector) -> Bool {
        if commandSelector == #selector(NSResponder.insertNewline(_:)) {
            NSLog("textView Enter key pressed!")
            return true
        }
        if commandSelector == #selector(NSResponder.deleteBackward(_:)) {
            NSLog("textView delete key pressed!")
            return true
        }
        
        if commandSelector == #selector(NSResponder.insertTab(_:)) {
            NSLog("textView tab key pressed!")
            return true
        }
        
        return false
    }
}

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/2237945.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

C# 实现对指定句柄的窗口进行键盘输入的实现

在C#中实现对指定句柄的窗口进行键盘操作,可以通过多种方式来实现。以下是一篇详细的指南,介绍如何在C#中实现这一功能。 1. 使用Windows API函数 在C#中,我们可以通过P/Invoke调用Windows API来实现对指定窗口的键盘操作。以下是一些关键的…

Spring Plugin与策略模式:打造动态可扩展的应用

目录 一、策略模式 二、Spring Plugin 2.1 Spring Plugin 实现策略模式开发 2.2 策略模式优缺点 三、Spring Plugin 原理 一、策略模式 策略模式是一种设计模式,它允许程序在运行中动态的选择不同的行为方式进行动态执行。策略模式的核心思想是将行为封装在一个个…

Word大珩助手:超大数字怎么读?35位数字?69位数字?

俄罗斯日前对谷歌开出了20000000000000000000000000000000000(35位数字)美元的罚款 这一数字远超全球GDP总和,消息一出很快就登上热搜。 面对这样一个庞大的数字,人们不禁好奇,这样的数字该如何读出来? …

asp.net文件防盗链

URLRewriter实现 可以参考下面的文章 代码 .net framework 新建asp.net framework的web项目,新建AntiTheftChainHandler using System.Web;namespace AntiTheftChainStu01.Handler {public class AntiTheftChainHandler : IHttpHandler{public bool IsReusable…

【含开题报告+文档+PPT+源码】基于SSM的蛋糕店销售管理系统的设计与实现

开题报告 在现代社会,蛋糕作为一种受欢迎的甜点,广泛应用于各种庆祝活动和节日。传统的蛋糕预订方式往往需要用户亲自到店面进行预订,预订流程繁琐,时间和地点限制也给用户带来了不便。随着智能手机和移动互联网的普及&#xff0…

政治经济学笔记

【拯救者】政治经济学速成(基础习题) 研究生产关系必须联系生产力和上层建筑 1.生产力与生产关系 生产力代表生产的物质内容,生产关系是生产的社会形式。生产力决定生产关系,生产关系对生产力具有 反作用 *其中的”反作用”指的是…

005.精读《B-Tree vs LSM-Tree》

文章目录 1. 引言:2. 精读2.1 性能指标2.2 B-tree2.3 LSM-tree2.4 性能对比 3. 写在最后 1. 引言: 在本期的技术深度解析中,我们将聚焦于数据领域的两个重要成员——B-Tree和LSM-Tree。这两种数据结构在数据管理系统中最为普遍且广泛采用的数…

关于 el-table 的合计行问题

目录 一.自定义合计行 二.合计行不展示,只有缩放/变大窗口或者F12弹出后台时才展示 三.合计行出现了表格滚动条下方 四.合计行整体样式的修改 五.合计行单元格样式修改 1.css 2.jsx方式 六.合计行单元格合并 一.自定义合计行 通过 show-summary 属性开启合计…

C++ | Leetcode C++题解之第554题砖墙

题目&#xff1a; 题解&#xff1a; class Solution { public:int leastBricks(vector<vector<int>>& wall) {unordered_map<int, int> cnt;for (auto& widths : wall) {int n widths.size();int sum 0;for (int i 0; i < n - 1; i) {sum wi…

如何使用 C# 编写一个修改文件时间属性的小工具?

下面是简鹿办公一个用 C# 编写的简单工具&#xff0c;它可以批量修改文件的创建时间、最后访问时间和最后修改时间。我们将使用 .NET Framework 或 .NET Core 来实现这个功能。 完整示例代码 1. 创建一个新的 C# 控制台应用程序 您可以使用 Visual Studio 或 .NET CLI 创建一个…

使用FTP与多个合作伙伴传文件,如何处理运维管理和数据安全问题

许多行业的企业使用FTP与外部客户、供应商等合作伙伴进行文件交换&#xff0c;如大型保险公司、研究所、IC设计企业、汽车制造厂商等。基于FTP可以满足企业与外部合作伙伴文件收发的基础需求&#xff0c;但在IT运维管理、数据安全保障及业务便利性上仍存在不同程度的缺陷和不足…

Simulink中Matlab function使用全局变量

目录 一. 引言二. 普通Matlab function使用全局变量三. Simulink中的Matlab function使用全局变量四. 如何利用Matlab function的全局变量施加随机噪声 一. 引言 最近发现了之前仿真中的一个问题&#xff0c;记录一下备忘。 Matlab function中有时候需要用到全局变量&#xf…

Jmeter的安装,设置中文,解决乱码问题

1.Jmeter安装 1-Jmeter如何下载 1---我这里提供一个下载快的方式 https://www.123684.com/s/lWZKVv-4jiav?提取码:4x4y 2---Jmeter官网下载地址 Apache JMeter - Download Apache JMeter 2-配置java环境 1---下载javaJDK 官方下载地址 https://www.oracle.com/java/techno…

深 度 学 习

神经网络基础 一、逻辑回归( Logic Regression ) 1 问题的模型 模型&#xff1a; 其中xx为输入量&#xff0c;y^​预测量&#xff0c;σ()激活函数。   逻辑回归主要用于二分类问题的拟合&#xff1a;0≤y^P(y1∣x)≤1&#xff0c;σ(z)如图&#xff1a; ​ 问题&#xff…

华为OD机试 - 最低位排序 - 数组(Java 2024 E卷 100分)

华为OD机试 2024E卷题库疯狂收录中&#xff0c;刷题点这里 专栏导读 本专栏收录于《华为OD机试&#xff08;JAVA&#xff09;真题&#xff08;E卷D卷A卷B卷C卷&#xff09;》。 刷的越多&#xff0c;抽中的概率越大&#xff0c;私信哪吒&#xff0c;备注华为OD&#xff0c;加…

C语言:文件操作2(又一万字?)

关于文件操作这章内容&#xff0c;因为知道内容较多所以我分两篇发了&#xff0c;但是还是没料到第二篇还是这么多&#xff0c;达到了一万多字&#xff01;&#xff01;&#xff01;作者本人真的将知识点进行了超级详解分析并且举了很多例子来帮助读者理解&#xff0c;本文章较…

RabbitMQ队列详细属性(重要)

RabbitMQ队列详细属性 1、队列的属性介绍1.1、Type&#xff1a;队列类型1.2、Name&#xff1a;队列名称1.3、Durability&#xff1a;声明队列是否持久化1.4、Auto delete&#xff1a; 是否自动删除1.5、Exclusive&#xff1a;1.6、Arguments&#xff1a;队列的其他属性&#xf…

【大模型】相比现有智能体(Agent)系统,微软新推出的 Magnetic-One 值得一看吗?

微软最近发布的Magnetic-One智能体系统在开源社区引发了广泛关注&#xff0c;因其在性能、灵活性和扩展性方面表现出色&#xff0c;被誉为目前开源社区最强的智能体解决方案。本文将从评测结果、工作原理、与现有智能体系统的比较三个方面&#xff0c;全面解析Magnetic-One的独…

C++——左值和右值的本质区别

左值和右值好干嘛&#xff1f; 深入理解左值和右值可以帮助我们对代码进行优化 一、什么是左值和右值 左值&#xff1a;有某种存储支持的变量 右值&#xff1a;临时值&#xff08;字面量、函数的结果&#xff09; Ⅰ右值是字面量 int yy 22;22本身就是一个临时的&#xf…

Rust-AOP编程实战

文章本天成,妙手偶得之。粹然无疵瑕,岂复须人为?君看古彝器,巧拙两无施。汉最近先秦,固已殊淳漓。胡部何为者,豪竹杂哀丝。后夔不复作,千载谁与期? ——《文章》宋陆游 【哲理】文章本是不加人工,天然而成的,是技艺高超的人在偶然间所得到的。其实作者所说的“天成”…