漠水 发表于 2015-2-4 15:14:14

为什么全局变量在回调函数中变化值不改变?求大神解答。。。

本帖最后由 漠水 于 2015-2-4 15:16 编辑

这里可以通过列表上面的文件下的“太烦”中组建输入会传递到全局变量all中,显示在主窗口,问题在代码247行 ,
问题在最后几行,我定义了一个全局变量line all ,为什么我在回调函数中改变all.n的值,在函数中all.n的值却没有变化。。。。,求解释
// 输入控件.cpp : 定义应用程序的入口点。
//

#include "stdafx.h"
#include "输入控件.h"
#include<stdio.h>
#include"strsafe.h"
#define MAX_LOADSTRING 100

//单个个体的数据
typedef struct
{
TCHAR Text;
}node;

typedef struct
{
node name;
int n;
}line;


// 全局变量:
HINSTANCE hInst; // 当前实例
TCHAR szTitle; // 标题栏文本
TCHAR szWindowClass; // 主窗口类名
line all; //定义一个可以存储的结构体

// 此代码模块中包含的函数的前向声明:
ATOM MyRegisterClass(HINSTANCE hInstance);
BOOL InitInstance(HINSTANCE, int);
LRESULT CALLBACK WndProc(HWND, UINT, WPARAM, LPARAM);
INT_PTR CALLBACK About(HWND, UINT, WPARAM, LPARAM);
INT_PTR CALLBACK Put(HWND, UINT, WPARAM, LPARAM);

int APIENTRY _tWinMain(HINSTANCE hInstance,
HINSTANCE hPrevInstance,
LPTSTR lpCmdLine,
int nCmdShow)
{
UNREFERENCED_PARAMETER(hPrevInstance);
UNREFERENCED_PARAMETER(lpCmdLine);

// TODO: 在此放置代码。
MSG msg;
HACCEL hAccelTable;

// 初始化全局字符串
LoadString(hInstance, IDS_APP_TITLE, szTitle, MAX_LOADSTRING);
LoadString(hInstance, IDC_MY, szWindowClass, MAX_LOADSTRING);
MyRegisterClass(hInstance);

// 执行应用程序初始化:
if (!InitInstance (hInstance, nCmdShow))
{
return FALSE;
}

hAccelTable = LoadAccelerators(hInstance, MAKEINTRESOURCE(IDC_MY));

// 主消息循环:
while (GetMessage(&msg, NULL, 0, 0))
{
if (!TranslateAccelerator(msg.hwnd, hAccelTable, &msg))
{
TranslateMessage(&msg);
DispatchMessage(&msg);
}
}

return (int) msg.wParam;
}



//
// 函数: MyRegisterClass()
//
// 目的: 注册窗口类。
//
// 注释:
//
// 仅当希望
// 此代码与添加到 Windows 95 中的“RegisterClassEx”
// 函数之前的 Win32 系统兼容时,才需要此函数及其用法。调用此函数十分重要,
// 这样应用程序就可以获得关联的
// “格式正确的”小图标。
//
ATOM MyRegisterClass(HINSTANCE hInstance)
{
WNDCLASSEX wcex;

wcex.cbSize = sizeof(WNDCLASSEX);

wcex.style = CS_HREDRAW | CS_VREDRAW;
wcex.lpfnWndProc = WndProc;
wcex.cbClsExtra = 0;
wcex.cbWndExtra = 0;
wcex.hInstance = hInstance;
wcex.hIcon = LoadIcon(hInstance, MAKEINTRESOURCE(IDI_MY));
wcex.hCursor = LoadCursor(NULL, IDC_ARROW);
wcex.hbrBackground = (HBRUSH)(COLOR_WINDOW+1);
wcex.lpszMenuName = MAKEINTRESOURCE(IDC_MY);
wcex.lpszClassName = szWindowClass;
wcex.hIconSm = LoadIcon(wcex.hInstance, MAKEINTRESOURCE(IDI_SMALL));

return RegisterClassEx(&wcex);
}

//
// 函数: InitInstance(HINSTANCE, int)
//
// 目的: 保存实例句柄并创建主窗口
//
// 注释:
//
// 在此函数中,我们在全局变量中保存实例句柄并
// 创建和显示主程序窗口。
//
BOOL InitInstance(HINSTANCE hInstance, int nCmdShow)
{
HWND hWnd;

hInst = hInstance; // 将实例句柄存储在全局变量中

hWnd = CreateWindow(szWindowClass, szTitle, WS_OVERLAPPEDWINDOW,
CW_USEDEFAULT, 0, CW_USEDEFAULT, 0, NULL, NULL, hInstance, NULL);

if (!hWnd)
{
return FALSE;
}

ShowWindow(hWnd, nCmdShow);
UpdateWindow(hWnd);

return TRUE;
}

//
// 函数: WndProc(HWND, UINT, WPARAM, LPARAM)
//
// 目的: 处理主窗口的消息。
//
// WM_COMMAND - 处理应用程序菜单
// WM_PAINT - 绘制主窗口
// WM_DESTROY - 发送退出消息并返回
//
//
LRESULT CALLBACK WndProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam)
{
int wmId, wmEvent;
TCHAR szBuffer; //缓存
PAINTSTRUCT ps;
HDC hdc;
size_t ss; //记录长度
all.n=0; //全局变量
switch (message)
{
case WM_COMMAND:
wmId = LOWORD(wParam);
wmEvent = HIWORD(wParam);
// 分析菜单选择:
switch (wmId)
{
case IDM_PUT:
if(DialogBox(hInst, MAKEINTRESOURCE(IDD_PUT), hWnd, Put))
InvalidateRect(hWnd, NULL, TRUE);
break;
case IDM_ABOUT:
DialogBox(hInst, MAKEINTRESOURCE(IDD_ABOUTBOX), hWnd, About);
break;
case IDM_EXIT:
DestroyWindow(hWnd);
break;
default:
return DefWindowProc(hWnd, message, wParam, lParam);
}
break;
case WM_PAINT:
hdc = BeginPaint(hWnd, &ps);
for(int k=0;k<=all.n;k++)
{
StringCchPrintf(szBuffer,128,TEXT("%d:%s"),all.n,all.name.Text); //记录要输出的字符串
StringCchLength(szBuffer,128,&ss); //记录长度
TextOut(hdc,all.n*15,0,szBuffer,ss); //输出位置(0,0)
}
EndPaint(hWnd, &ps);
break;
case WM_DESTROY:
PostQuitMessage(0);
break;
default:
return DefWindowProc(hWnd, message, wParam, lParam);
}
return 0;
}

// “关于”框的消息处理程序。
INT_PTR CALLBACK About(HWND hDlg, UINT message, WPARAM wParam, LPARAM lParam)
{
UNREFERENCED_PARAMETER(lParam);
switch (message)
{
case WM_INITDIALOG:
return (INT_PTR)TRUE;

case WM_COMMAND:
if (LOWORD(wParam) == IDOK || LOWORD(wParam) == IDCANCEL)
{
EndDialog(hDlg, LOWORD(wParam));
return (INT_PTR)TRUE;
}
break;
}
return (INT_PTR)FALSE;
}

// “put”框的消息处理程序。
INT_PTR CALLBACK Put(HWND hDlg, UINT message, WPARAM wParam, LPARAM lParam)
{

static TCHAR Text;
static HWND EDIT;
UNREFERENCED_PARAMETER(lParam);
switch (message)
{
case WM_INITDIALOG:
return (INT_PTR)TRUE;
case WM_COMMAND:
EDIT = GetDlgItem(hDlg,IDC_EDIT1);//获取文本框句柄
switch(LOWORD(wParam))
{
case IDC_EDIT1:
switch(HIWORD(wParam))
{
case EN_UPDATE:
GetWindowText(EDIT,Text,20);
break;
}
break;
case IDOK:
_tcscpy_s(all.name.Text, sizeof(all.name.Text)/sizeof(all.name.Text), Text);
//如何将一个字符串的内容复制到另一个字符串里
// MessageBox(hDlg,Text,all.name.Text,MB_OK);

//问题在这里,为什么all.n的值不变
all.n+=1; //值传递不会返回的!同类型同数值的不同数据?



EndDialog(hDlg, LOWORD(wParam));
return (INT_PTR)TRUE;
case IDCANCEL:
EndDialog(hDlg, LOWORD(wParam));
return (INT_PTR)TRUE;
}
break;
}
return (INT_PTR)FALSE;
}



lixiaoshuai 发表于 2015-2-4 15:14:15

。。。。。。。。。。。。。。下次能贴部分代码吗。。。

漠水 发表于 2015-2-4 19:58:39

自问自答有点伤心。。。。改变后的源代码:
// 输入控件.cpp : 定义应用程序的入口点。
//

#include "stdafx.h"
#include "输入控件.h"
#include<stdio.h>
#include"strsafe.h"
#define MAX_LOADSTRING 100

//单个个体的数据
typedef struct
{
        TCHAR Text;
}node;               

typedef struct
{
        node name;
        int n;
}line;


// 全局变量:
HINSTANCE hInst;                                                                // 当前实例
TCHAR szTitle;                                        // 标题栏文本
TCHAR szWindowClass;                        // 主窗口类名
line all;                                                                                //定义一个可以存储的结构体

// 此代码模块中包含的函数的前向声明:
ATOM                                MyRegisterClass(HINSTANCE hInstance);
BOOL                                InitInstance(HINSTANCE, int);
LRESULT CALLBACK        WndProc(HWND, UINT, WPARAM, LPARAM);
INT_PTR CALLBACK        About(HWND, UINT, WPARAM, LPARAM);
INT_PTR CALLBACK        Put(HWND, UINT, WPARAM, LPARAM);

int APIENTRY _tWinMain(HINSTANCE hInstance,
                     HINSTANCE hPrevInstance,
                     LPTSTR    lpCmdLine,
                     int       nCmdShow)
{
        UNREFERENCED_PARAMETER(hPrevInstance);
        UNREFERENCED_PARAMETER(lpCmdLine);

        // TODO: 在此放置代码。
        MSG msg;
        HACCEL hAccelTable;

        // 初始化全局字符串
        LoadString(hInstance, IDS_APP_TITLE, szTitle, MAX_LOADSTRING);
        LoadString(hInstance, IDC_MY, szWindowClass, MAX_LOADSTRING);
        MyRegisterClass(hInstance);

        // 执行应用程序初始化:
        if (!InitInstance (hInstance, nCmdShow))
        {
                return FALSE;
        }

        hAccelTable = LoadAccelerators(hInstance, MAKEINTRESOURCE(IDC_MY));

        // 主消息循环:
        while (GetMessage(&msg, NULL, 0, 0))
        {
                if (!TranslateAccelerator(msg.hwnd, hAccelTable, &msg))
                {
                        TranslateMessage(&msg);
                        DispatchMessage(&msg);
                }
        }

        return (int) msg.wParam;
}



//
//函数: MyRegisterClass()
//
//目的: 注册窗口类。
//
//注释:
//
//    仅当希望
//    此代码与添加到 Windows 95 中的“RegisterClassEx”
//    函数之前的 Win32 系统兼容时,才需要此函数及其用法。调用此函数十分重要,
//    这样应用程序就可以获得关联的
//    “格式正确的”小图标。
//
ATOM MyRegisterClass(HINSTANCE hInstance)
{
        WNDCLASSEX wcex;

        wcex.cbSize = sizeof(WNDCLASSEX);

        wcex.style                        = CS_HREDRAW | CS_VREDRAW;
        wcex.lpfnWndProc        = WndProc;
        wcex.cbClsExtra                = 0;
        wcex.cbWndExtra                = 0;
        wcex.hInstance                = hInstance;
        wcex.hIcon                        = LoadIcon(hInstance, MAKEINTRESOURCE(IDI_MY));
        wcex.hCursor                = LoadCursor(NULL, IDC_ARROW);
        wcex.hbrBackground        = (HBRUSH)(COLOR_WINDOW+1);
        wcex.lpszMenuName        = MAKEINTRESOURCE(IDC_MY);
        wcex.lpszClassName        = szWindowClass;
        wcex.hIconSm                = LoadIcon(wcex.hInstance, MAKEINTRESOURCE(IDI_SMALL));

        return RegisterClassEx(&wcex);
}

//
//   函数: InitInstance(HINSTANCE, int)
//
//   目的: 保存实例句柄并创建主窗口
//
//   注释:
//
//      在此函数中,我们在全局变量中保存实例句柄并
//      创建和显示主程序窗口。
//
BOOL InitInstance(HINSTANCE hInstance, int nCmdShow)
{
   HWND hWnd;

   hInst = hInstance; // 将实例句柄存储在全局变量中

   hWnd = CreateWindow(szWindowClass, szTitle, WS_OVERLAPPEDWINDOW,
      CW_USEDEFAULT, 0, CW_USEDEFAULT, 0, NULL, NULL, hInstance, NULL);

   if (!hWnd)
   {
      return FALSE;
   }

   ShowWindow(hWnd, nCmdShow);
   UpdateWindow(hWnd);

   return TRUE;
}

//
//函数: WndProc(HWND, UINT, WPARAM, LPARAM)
//
//目的: 处理主窗口的消息。
//
//WM_COMMAND        - 处理应用程序菜单
//WM_PAINT        - 绘制主窗口
//WM_DESTROY        - 发送退出消息并返回
//
//
LRESULT CALLBACK WndProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam)
{
        int wmId, wmEvent;
        TCHAR szBuffer;                //缓存
        PAINTSTRUCT ps;
        HDC hdc;
        size_t ss;                                        //记录长度
        //all.n=0;                                        //全局变量
        switch (message)
        {
        case WM_CREATE:
                all.n=0;                        //全局变量数据改变必须在事件驱动中
                break;
        case WM_COMMAND:
                wmId    = LOWORD(wParam);
                wmEvent = HIWORD(wParam);
                // 分析菜单选择:
                switch (wmId)
                {
                case IDM_PUT:
                        if(DialogBox(hInst, MAKEINTRESOURCE(IDD_PUT), hWnd, Put))
                        InvalidateRect(hWnd, NULL, TRUE);
                        break;
                case IDM_ABOUT:
                        DialogBox(hInst, MAKEINTRESOURCE(IDD_ABOUTBOX), hWnd, About);
                        break;
                case IDM_EXIT:
                        DestroyWindow(hWnd);
                        break;
                default:
                        return DefWindowProc(hWnd, message, wParam, lParam);
                }
                break;
        case WM_PAINT:
                hdc = BeginPaint(hWnd, &ps);
                for(int k=0;k<=all.n;k++)
                {
                //StringCchPrintf(szBuffer,128,TEXT("%d:%s"),all.n,all.name.Text);       //记录要输出的字符串
                StringCchPrintf(szBuffer,128,all.name.Text);       //记录要输出的字符串
                StringCchLength(szBuffer,128,&ss);                       //记录长度
                TextOut(hdc,0,k*15,szBuffer,ss);                //输出位置(0,0)
                }
                EndPaint(hWnd, &ps);
                break;
        case WM_DESTROY:
                PostQuitMessage(0);
                break;
        default:
                return DefWindowProc(hWnd, message, wParam, lParam);
        }
        return 0;
}

// “关于”框的消息处理程序。
INT_PTR CALLBACK About(HWND hDlg, UINT message, WPARAM wParam, LPARAM lParam)
{
        UNREFERENCED_PARAMETER(lParam);
        switch (message)
        {
        case WM_INITDIALOG:
                return (INT_PTR)TRUE;

        case WM_COMMAND:
                if (LOWORD(wParam) == IDOK || LOWORD(wParam) == IDCANCEL)
                {
                        EndDialog(hDlg, LOWORD(wParam));
                        return (INT_PTR)TRUE;
                }
                break;
        }
        return (INT_PTR)FALSE;
}

// “put”框的消息处理程序。
INT_PTR CALLBACK Put(HWND hDlg, UINT message, WPARAM wParam, LPARAM lParam)
{

        static TCHARText;
        static HWND EDIT;
        UNREFERENCED_PARAMETER(lParam);
        switch (message)
        {
        case WM_INITDIALOG:
                return (INT_PTR)TRUE;
        case WM_COMMAND:
                EDIT = GetDlgItem(hDlg,IDC_EDIT1);//获取文本框句柄
                switch(LOWORD(wParam))
                {
                  case IDC_EDIT1:
                           switch(HIWORD(wParam))
                                {
                               case EN_UPDATE:
                               GetWindowText(EDIT,Text,20);
                               break;
                                }
                                break;
                case IDOK:
                       _tcscpy_s(all.name.Text, sizeof(all.name.Text)/sizeof(all.name.Text), Text);
            //如何将一个字符串的内容复制到另一个字符串里
                        MessageBox(hDlg,Text,all.name.Text,MB_OK);

                        //问题在这里,为什么all.n的值不变
                       all.n+=1;         //值传递不会返回的!同类型同数值的不同数据?



                        EndDialog(hDlg, LOWORD(wParam));
                        return (INT_PTR)TRUE;
                case IDCANCEL:
                        EndDialog(hDlg, LOWORD(wParam));
                        return (INT_PTR)TRUE;
                }
                break;
        }
        return (INT_PTR)FALSE;
}

liyf 发表于 2015-2-6 07:37:20

debug一遍遍就知道了

漠水 发表于 2015-2-7 17:10:16

lixiaoshuai 发表于 2015-2-4 15:14
。。。。。。。。。。。。。。下次能贴部分代码吗。。。

我怕说不清楚。。。。

lixiaoshuai 发表于 2015-2-7 18:11:20

漠水 发表于 2015-2-7 17:10
我怕说不清楚。。。。

恩,编程有个kiss原则,keep it simple and stupid 浮躁的社会没人有耐心慢慢啦~\(≧▽≦) 都去泡妹子了~~
页: [1]
查看完整版本: 为什么全局变量在回调函数中变化值不改变?求大神解答。。。