2011-05-06 2 views
1

다음은 작성할 수있는 문제에 대한 가장 짧은 컴파일 가능한 데모입니다.GHashTable은 두 개의 동일한 입력에 완전히 다르게 응답합니다.

끝 부분의 printf 호출을 보면 출력이 다음과 같습니다. 나는 왜 이라는 정확히 같은 두 문장이 정확히 일 수 있는지 전혀 모른다. 아마도 입력 유형과 관련이 있지만 실제로 무엇이 될지 알 수는 없습니다.

#include <gtk/gtk.h> 
#include <libxml/xmlmemory.h> 
#include <libxml/parser.h> 
int 
main (int argc, char *argv[]) 
{ 
    gtk_init (&argc, &argv); 
    GtkBuilder * builder = gtk_builder_new(); 
    GHashTable * table = g_hash_table_new(NULL,NULL); 
    int i; 
    char builderdoc[] = "<?xml version=\"1.0\"?>" 
"<interface>" 
" <requires lib=\"gtk+\" version=\"2.16\"/>" 
" <!-- interface-naming-policy project-wide -->" 
" <object class=\"GtkCheckButton\" id=\"checkbutton1\">" 
" </object>" 
"</interface>"; 

    // Load gtkbuilder 
    gtk_builder_add_from_string (builder, builderdoc, sizeof(builderdoc),NULL); 

    char * buffer[][2] = { 
    {"log","checkbutton1"} 
    }; 

    // Load array of widgets into hash table (Shortened) 
    for(i = 0; i < sizeof(buffer)/sizeof(char *)/2; i++){ 
     g_hash_table_insert(table,(gchar *) buffer[i][0],gtk_builder_get_object (builder, (gchar *) buffer[i][1])); 
    } 


    // Load xml doc 
    xmlDocPtr doc; 
    xmlNodePtr cur; 
    xmlNodePtr cur2; 
    char xmldoc[] = "<?xml version=\"1.0\"?>" 
        "<CsSettings>" 
        "<options>" 
        "<check name=\"log\" value=\"1\" />" 
        "</options>" 
        "</CsSettings>"; 

    doc = xmlParseMemory(xmldoc, (int) sizeof(xmldoc)); 
    cur = xmlDocGetRootElement(doc); 
    cur = cur->xmlChildrenNode; 

    // Find what we're looking for 
    while (cur != NULL){ 
     if(xmlStrEqual(cur->name, (xmlChar *) "options")){ 
      cur2 = cur->xmlChildrenNode; 
      while (cur2 != NULL){ 
       if(xmlStrEqual(cur2->name, (xmlChar *) "check")){ 
        // We've found it, now print some output 
        printf("Plain old lookup: g_hash_table_lookup(table,\"log\"): %p\n",g_hash_table_lookup(table,"log")); 
        printf("Variable lookup : g_hash_table_lookup(table,\"%s\"): %p\n",(gchar *) xmlGetProp(cur2, (xmlChar *) "name"),g_hash_table_lookup(table,(gchar *) xmlGetProp(cur2, (xmlChar *) "name"))); 
        printf("Xml says we should lookup: '%s'\n",(gchar *) xmlGetProp(cur2, (xmlChar *) "name")); 

       } 
       cur2 = cur2->next; 
      } 
     }  
     cur = cur->next; 
    } 

} 

그리고 영광스럽게 혼란 출력 :

Plain old lookup: g_hash_table_lookup(table,"log"): 0x1e369a0 
Variable lookup : g_hash_table_lookup(table,"log"): (nil) 
Xml says we should lookup: 'log' 

답변

3

생성자에 어떤 해시거나 같은 기능을 설정하지 않기 때문에 당신은이 경우 직접 해시에, 해시 테이블에서 예기치 않은 동작을 받고 수 있습니다 포인터에 g_direct_hash()g_direct_equal() 기능이 적용됩니다.

표의 키가 gchar * 인 경우 g_str_hashg_str_equal을 사용합니다. 이런 식으로 뭔가가 테이블을 초기화하기 : 포인터에

GHashTable * table = g_hash_table_new(g_str_hash,g_str_equal);

직접 해싱은 좋은 생각이 아니다, 해시 테이블의 키 포인터가 참조되는 느릅 나무하는 내용 인 경우. 이 문제가 해결되면 알려주세요.

+1

믿을만한 사람. 전에는 그걸 사용했지만 그 목적을 알 수 없었습니다. 대단히 감사합니다. P –