发帖
1 0 0

学习socket从这里开始1

ddyty
高级会员

3

主题

49

回帖

889

积分

高级会员

积分
889
技术杂谈 76 1 5 天前

学习socket从这里开始1

首先介绍一个socket获取天气服务的实例,随后我会逐步的使用小安派实现socket 链接天气服务

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <sys/socket.h>
#include <netdb.h>

#define PORT "80"
#define HOST "api.seniverse.com"

int main()
{
    // 初始化 addrinfo 结构体,用于指定要连接的服务器的信息
    struct addrinfo hints, *servinfo, *p;
    int rv, sockfd;
    char request[256];
    char buffer[1024];
    int numbytes;
    int found_start = 0;

    // 清空 hints 结构体,设置地址族为不指定,套接字类型为流式套接字(TCP)
    memset(&hints, 0, sizeof hints);
    hints.ai_family = AF_UNSPEC;
    hints.ai_socktype = SOCK_STREAM;

    // 获取指定主机和服务的信息,存储在 servinfo 链表中
    if ((rv = getaddrinfo(HOST, PORT, &hints, &servinfo)) != 0)
    {
        fprintf(stderr, "getaddrinfo: %s\n", gai_strerror(rv));
        return 1;
    }

    // 遍历 servinfo 链表,尝试创建并连接套接字
    for (p = servinfo; p != NULL; p = p->ai_next)
    {
        if ((sockfd = socket(p->ai_family, p->ai_socktype, p->ai_protocol)) == -1)
        {
            continue;
        }

        if (connect(sockfd, p->ai_addr, p->ai_addrlen) == -1)
        {
            close(sockfd);
            continue;
        }

        break;
    }

    // 如果没有成功连接到任何地址,输出错误信息并退出
    if (p == NULL)
    {
        fprintf(stderr, "failed to connect\n");
        return 2;
    }

    // 释放 servinfo 结构体占用的内存
    freeaddrinfo(servinfo);

    // 构造 HTTP GET 请求字符串
    snprintf(request, sizeof(request), "GET /v3/weather/now.json?key=SOGXnVRmQE-ISnQRo&location=hangzhou&language=zh-Hans&unit=c HTTP/1.1\r\nHost: %s\r\nConnection: close\r\n\r\n", HOST);
    // 发送 HTTP 请求到服务器
    send(sockfd, request, strlen(request), 0);

    // 接收服务器返回的数据,直到没有更多数据可接收
    while ((numbytes = recv(sockfd, buffer, sizeof(buffer) - 1, 0)) > 0)
    {
        buffer[numbytes] = '\0';

        // 如果还没有找到 JSON 数据的开始部分
        if (!found_start)
        {
            // 查找第一个 '{' 的位置
            char *start = strchr(buffer, '{');
            if (start != NULL)
            {
                found_start = 1;
                printf("%s", start);
            }
            else
            {
                // 如果这一块数据中没有找到 '{',继续接收下一块数据
                continue;
            }
        }
        else
        {
            // 如果已经找到 JSON 数据的开始部分,直接打印
            printf("%s", buffer);
        }
    }

    // 关闭套接字
    close(sockfd);

    return 0;
}

在linux环境下 gcc main.c -o main

./main

就可以看到天气了

image.png

──── 0人觉得很赞 ────

使用道具 举报

开始分享了啊
您需要登录后才可以回帖 立即登录
高级模式
返回
统计信息
  • 会员数: 28167 个
  • 话题数: 39945 篇