c#模仿内置 Socket.Receive(无需 out/ref,直接写回数据)

、正确实现:模仿内置 Socket.Receive(无需 out/ref,直接写回数据)

核心:去掉 out/ref,利用数组「引用类型」的特性,直接修改数组内容(和内置 Socket 逻辑一致),调用时无需加任何关键字:

cs 复制代码
public class Newsocket
{
    // 模拟内置 Socket 的 Receive 逻辑(无 out/ref,数组默认按引用传递)
    public int Receive(byte[] buffer)
    {
        // 1. 校验参数(和内置 Socket 保持一致)
        if (buffer == null)
            throw new ArgumentNullException(nameof(buffer));
        if (buffer.Length == 0)
            throw new ArgumentException("缓冲区长度不能为0", nameof(buffer));

        try
        {
            // 2. 模拟接收数据(替换为你的实际逻辑:如从 Tool2 取数据/原生 Socket 接收)
            // 示例:模拟接收到 10 字节数据,写入调用方的 buffer
            byte[] receivedData = new byte[] { 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0A };
            
            // 3. 核心:将数据写入调用方的 buffer(数组是引用类型,直接修改内容)
            int copyLength = Math.Min(receivedData.Length, buffer.Length); // 避免越界
            Array.Copy(receivedData, 0, buffer, 0, copyLength);
            
            // 4. 多余位置置0(可选,和内置 Socket 行为一致)
            if (copyLength < buffer.Length)
                Array.Clear(buffer, copyLength, buffer.Length - copyLength);

            // 5. 返回实际接收的字节数(和内置 Socket 保持一致)
            return copyLength;
        }
        catch (Exception ex)
        {
            Console.WriteLine($"接收异常:{ex.Message}");
            return -1; // 异常返回-1,内置 Socket 会抛异常,你可按需调整
        }
    }
}

// 你的静态类(无变化)
public static class chuankou
{
    public static Newsocket socket = new Newsocket();
}
调用(和内置 Socket 完全一致,无需任何关键字)

csharp

运行

复制代码
// 和调用内置 Socket.Receive 一模一样,无任何关键字,无 CS1620 错误
byte[] readBuffer3 = new byte[53];
int recvLength = chuankou.socket.Receive(readBuffer3);

// 处理结果:recvLength 是实际接收的字节数,readBuffer3 前 recvLength 字节是有效数据
if (recvLength > 0)
{
    Console.WriteLine($"接收 {recvLength} 字节,数据:{BitConverter.ToString(readBuffer3, 0, recvLength)}");
}

三、核心原理:数组的 "值传递" vs "引用传递"

很多人误以为 out/ref 是修改数组的唯一方式,其实是对 C# 类型的误解:

类型 参数传递方式 能否修改内容 能否修改引用 调用是否需关键字
引用类型(数组 / 对象) 普通值传递(无修饰) ✅ 可以(如修改 buffer [0]) ❌ 不可以(如 buffer = new byte [10]) ❌ 无需
任意类型 ref 修饰 ✅ 可以 ✅ 可以 ✅ 需加 ref
任意类型 out 修饰 ✅ 可以 ✅ 可以 ✅ 需加 out
  • 内置 Socket.Receive 只需要修改数组内容 ,因此用「普通值传递」即可,无需 out/ref
  • 你之前错误地用了 out/ref,是 "过度设计",导致调用时必须加关键字。

总结

  1. 错误根源 :你的 Receive 方法加了 out/ref 修饰,而内置 Socket.Receive 无任何修饰;
  2. 核心修正 :去掉 out/ref,利用数组「引用类型」特性直接修改内容(和内置 Socket 逻辑一致);
  3. 调用体验 :修改后 chuankou.socket.Receive(readBuffer3) 无需任何关键字,和调用内置 Socket 完全一样,彻底消除 CS1620 错误;
  4. 关键规则 :仅当需要修改「变量的引用」(如 buffer = new byte[10])时,才需要 out/ref;仅修改数组内容,无需加任何修饰。

按上述代码实现后,你的 Receive 方法会和内置 Socket.Receive 行为完全一致,调用简洁且无语法错误。

相关推荐
爱内卷的学霸一枚2 小时前
Python并发编程与性能优化实战指南
开发语言·python·性能优化
jaysee-sjc2 小时前
【项目二】用GUI编程实现石头迷阵游戏
java·开发语言·算法·游戏
一位搞嵌入式的 genius2 小时前
从 URL 到渲染:JavaScript 性能优化全链路指南
开发语言·前端·javascript·性能优化
ID_180079054732 小时前
Python结合淘宝关键词API进行商品数据挖掘与
开发语言·python·数据挖掘
天天进步20152 小时前
Motia性能进阶与未来:从现有源码推测 Rust 重构之路
开发语言·重构·rust
星空下的月光影子2 小时前
易语言开发从入门到精通:补充篇·办公+桌面自动化深度实战·Word/Excel/PDF联合处理·模拟键鼠·消息推送·定时任务调度
开发语言
兩尛2 小时前
2. 两数相加 c++
开发语言·c++
Z9fish2 小时前
sse哈工大C语言编程练习22
c语言·开发语言·算法
小二·2 小时前
Go 语言系统编程与云原生开发实战(第12篇)云原生部署实战:Helm Chart × GitOps × 多环境管理(生产级落地)
开发语言·云原生·golang