Re: [問題] 關於Class指標的觀念

看板C_and_CPP (C/C++)作者 (我要加入劍道社!)時間11年前 (2013/08/26 23:57), 編輯推噓14(140190)
留言204則, 17人參與, 最新討論串3/19 (看更多)

08/26 20:02,
看來各位好像不太能理解其中的道理,各位要記得,記憶體位址
08/26 20:02

08/26 20:03,
永遠都是「無號數整數型態」,float 與 double 是屬於實數型
08/26 20:03
struct A { void func() {} }; void (A::*p) = &A::func; cout << (unsigned long)p << endl; VC++ 2012 編譯結果: hello.cpp(12) : error C2440: '型別轉換' : 無法由 'void (__thiscall main::A::* )(void)' 轉換為 'unsigned long' 沒有可以進行此轉換的內容 啊不是說都無號整數?為什麼轉不過去啊? 不然轉指標好了 cout << (int*)p << endl; VC++ 2012 編譯結果: hello.cpp(12) : error C2440: '型別轉換' : 無法由 'void (__thiscall main::A::* )(void)' 轉換為 'int*' 沒有可以進行此轉換的內容 啊不是說實作上可行嗎? 我試了一堆 compiler 都不給我過啊! 好啦我還沒測 VC6,搞不好這個特異的 compiler 還真的能編

08/26 21:12,
還蠻好奇有那些機器的記憶體位址是違反無號正整數?
08/26 21:12

08/26 21:13,
總覺得目前的眼界還是太小XDlll感覺有好多不可思議的事
08/26 21:13
上面那個例子就是了 不用什麼特別的機器 你現在在用的電腦也一樣編不過

08/26 21:24,
記憶體位址對任何機器來說都是屬於連續的位址編號,並不會有
08/26 21:24

08/26 21:25,
所謂的違反問題,就好像住家地址不可能以自已的姓名代表一樣
08/26 21:25
還連續編號勒 告訴我上面的 p 到底是幾號啊! -- ※ 發信站: 批踢踢實業坊(ptt.cc) ◆ From: 202.39.238.242

08/26 23:59, , 1F
我相信他等等會開assembler然後把call rel/call abs的
08/26 23:59, 1F

08/26 23:59, , 2F
target address拿出來跟你說就是那個值...
08/26 23:59, 2F

08/26 23:59, , 3F
s/assembler/assembly
08/26 23:59, 3F

08/27 00:27, , 4F
那我好心提醒一下 那個值是錯的
08/27 00:27, 4F

08/27 01:01, , 5F
其實這個例子滿有趣的,可以試看看這個 :
08/27 01:01, 5F

08/27 01:03, , 6F
cout << &A::func;
08/27 01:03, 6F

08/27 01:04, , 7F
會發現什麼都沒有,可以思考看看為什麼會這樣.
08/27 01:04, 7F

08/27 01:21, , 8F
L 大大,一個大陣列的記憶體位址是不是連續的您應該知道吧?
08/27 01:21, 8F

08/27 01:28, , 9F
哈哈. G大又本末倒置了
08/27 01:28, 9F

08/27 01:29, , 10F
Feis : 此話怎說?
08/27 01:29, 10F

08/27 01:35, , 11F
那不是我要思考的,是你要自圓其說
08/27 01:35, 11F

08/27 01:35, , 12F
你說記憶體位址都是無號整數 但顯然不是這樣
08/27 01:35, 12F

08/27 01:40, , 13F
話說是不是應該是 void (A::*p)() = &A::func; 我醉了嗎 Q_Q
08/27 01:40, 13F
不不是我醉了 今天應酬多喝了一杯 tequila shot 害我犯了這種低級錯誤

08/27 01:42, , 14F
L 大大,竟然您提出了問題,但您確定有思考過這個問題為什麼
08/27 01:42, 14F

08/27 01:43, , 15F
會發生嗎?如果不思考而直接提問想要對方自圓其說,這樣說好
08/27 01:43, 15F
啊?你在跟誰說話啊? 我當然知道答案啊!因為 p 不是單純的無號整數嘛! 至於 p 是什麼,要看 compiler 大部份的 compiler 都是採用....等一下為什麼我要跟你說這個啊? 你不是堅持 p 是無號整數嗎?我提出反例結果竟然是你要我先思考這個問題?

08/27 01:43, , 16F
那G大可以說說高見嗎?
08/27 01:43, 16F

08/27 01:44, , 17F
像不符合事實吧?
08/27 01:44, 17F

08/27 01:46, , 18F
如果「知其然,並不知其所然」,這是每個人的必經之路,唯有抱
08/27 01:46, 18F

08/27 01:46, , 19F
著一顆學習的心態才能使自已成長.
08/27 01:46, 19F
※ 編輯: littleshan 來自: 202.39.238.242 (08/27 02:01)

08/27 01:54, , 20F
所以呢? cout << &A::func 什麼都沒有又是哪招?
08/27 01:54, 20F

08/27 02:55, , 21F
在我的電腦上,如果要輸出「類別內的函式或是資料成員」的
08/27 02:55, 21F

08/27 02:56, , 22F
位址,有可能會看到不正確的結果,如果以啟動 Debug 模式,可
08/27 02:56, 22F

08/27 02:57, , 23F
以看到 p 的確是有位址資料,但輸出是 0 或是 1,顯然這個跟
08/27 02:57, 23F

08/27 02:58, , 24F
編譯器實作有關係,所以 p 並不是沒有資料,而是被編譯器隱藏
08/27 02:58, 24F

08/27 03:00, , 25F
起來不讓您看到,為什麼會這樣說呢?當編譯器遇到這個敘述 :
08/27 03:00, 25F

08/27 03:04, , 26F
void(A::*pv)(void) = &A::func;
08/27 03:04, 26F

08/27 03:05, , 27F
cout << pv; // 這個敘述無義意
08/27 03:05, 27F
還有 137 則推文
08/27 19:45, , 165F
抓上一層是 __builtin_return_address(0) 才對,這邊也錯
08/27 19:45, 165F

08/27 19:55, , 166F
K 大大,我在前面說過,記憶體存取範圍會因為作業系統使用了
08/27 19:55, 166F

08/27 19:57, , 167F
記憶體管理而讓使用者覺得位址好像沒有連續,前面也說到不可
08/27 19:57, 167F

08/27 19:58, , 168F
能全部都給自已使用,0 ~ FFFFFFFF 只是一個範圍,從那裡開始
08/27 19:58, 168F

08/27 19:59, , 169F
是作業系統自已決定,程式設計師只能使用作業系統給的有限範
08/27 19:59, 169F

08/27 20:00, , 170F
圍內使用.
08/27 20:00, 170F

08/27 20:18, , 171F
S 大大,即然您知道位址是 Segment 與 Offset 組成,那為什麼
08/27 20:18, 171F

08/27 20:18, , 172F
printf("p: %s\n", p) 就可以看到位址
08/27 20:18, 172F

08/27 20:19, , 173F
不知道 cout 為什麼不行
08/27 20:19, 173F

08/27 20:19, , 174F
不會覺得是正整數呢?可以請您說明一下嗎,謝謝
08/27 20:19, 174F

08/27 20:22, , 175F
pointer應該是%p吧,%s是字串
08/27 20:22, 175F

08/27 20:23, , 176F
[請問] 0100:0000 與 0000:1000 有何不同?
08/27 20:23, 176F

08/27 20:24, , 177F
D 大大說到重點了,各位可以想看看為什麼 printf() 函式可以
08/27 20:24, 177F

08/27 20:24, , 178F
看到位址?
08/27 20:24, 178F

08/27 20:25, , 179F
我就知道你要直接切進DOS4GW模式 XD
08/27 20:25, 179F

08/27 20:43, , 180F
沒想到本板還看得到 dos4gw XD
08/27 20:43, 180F

08/27 20:49, , 181F
elenya: 感謝更正, 是 %p 沒錯。
08/27 20:49, 181F

08/27 20:54, , 182F
在 16 bit 下, 0100:0000 與 0000:1000 並沒有不同,因為它
08/27 20:54, 182F

08/27 20:56, , 183F
們都是代表同一個實體位址,也就是 16 進位絕對位址 1000
08/27 20:56, 183F

08/27 20:58, , 184F
真實模式下絕對位址沒有不同沒錯,當作word或byte address時
08/27 20:58, 184F

08/27 20:59, , 185F
取到的資料相同沒錯,但位於不一樣的segment,基本上是不一樣
08/27 20:59, 185F

08/27 21:01, , 186F
的long pointer,加上F000 offset一個指到10000一個是00000
08/27 21:01, 186F

08/27 21:02, , 187F
不過在C&C++板討論assembly我是不是應該要自請水桶...
08/27 21:02, 187F

08/27 21:03, , 188F
E 大,這個問題是屬於組合語言的部份了.
08/27 21:03, 188F

08/27 21:04, , 189F
這個問題可以另外討論,但我要強調的是,不管是使用那一種記
08/27 21:04, 189F

08/27 21:05, , 190F
憶體表示法,它們永遠都是屬於「無號正整數」,其實我還滿想
08/27 21:05, 190F

08/27 21:06, , 191F
看用負數的方式來表示記憶體位址呢!
08/27 21:06, 191F

08/27 21:12, , 192F
負數可以啦,不過用不著特別去計較它是正數還是負數
08/27 21:12, 192F

08/27 21:13, , 193F
反正只討論flat model的話,比0小就算負數了,你要講無號也通
08/27 21:13, 193F

08/27 21:16, , 194F
非flat model還有很多畸形architecture可以討論
08/27 21:16, 194F

08/27 21:17, , 195F
我看到前排這位8051在舉手了,給我坐下,不關你的事。
08/27 21:17, 195F

08/27 21:19, , 196F
並非計較,只是強調觀念,而且我很好奇的是,即然存取範圍是
08/27 21:19, 196F

08/27 21:19, , 197F
0 ~ FFFFFFFF,那為什麼會有負數呢?
08/27 21:19, 197F

08/27 21:20, , 198F
難道 FFFFFFFF 可以解釋成 -1 ?
08/27 21:20, 198F

08/27 21:25, , 199F
而且您說的 0100:0000 與 0000:1000 位移 F000 後會不一樣,
08/27 21:25, 199F

08/27 21:26, , 200F
可以另外討論.
08/27 21:26, 200F

08/27 21:38, , 201F
記憶體(硬體)是人設計的,他們也可以做一個記憶體,你存取
08/27 21:38, 201F

08/27 21:39, , 202F
某些特定的值就會出事,os 或是 程式要自己想辦法避開
08/27 21:39, 202F

08/27 21:40, , 203F
現在的記憶體幾乎都是連續整數只是方便而已,未來會怎麼樣
08/27 21:40, 203F

08/27 21:40, , 204F
誰也不知道
08/27 21:40, 204F
文章代碼(AID): #1I6thzPw (C_and_CPP)
討論串 (同標題文章)
文章代碼(AID): #1I6thzPw (C_and_CPP)