猿问

Golang 访问通用结构的数据元素

我将有一个应用程序,其中包含许多遵循 Req/Rsp 设计的消息。下面实现的是消息 Foo 的单个 Req/Rsp。Req 将遵循用于处理消息并返回响应的通用接口。所有 Rsp 消息都将嵌入 MHRSP 结构。我想在 ProcessRequest 方法之外设置响应状态。我遇到的问题是由下面标记的代码块导致的运行时错误Problem Area


panic: interface conversion: interface {} is *main.FooRsp, not main.MHRSP


由于我将有很多消息,而不仅仅是 FooRsp,因此转换为 FooRsp 不是解决方案,所以问题是,我如何以通用方式处理这个问题(即能够为任何 Rsp 设置成功和错误消息)?


使用 GDB Online 编译的代码:https ://www.onlinegdb.com/online_go_compiler


/******************************************************************************

Welcome to GDB Online.

GDB online is an online compiler and debugger tool for C, C++, Python, Java, PHP, Ruby, Perl,

C#, VB, Swift, Pascal, Fortran, Haskell, Objective-C, Assembly, HTML, CSS, JS, SQLite, Prolog.

Code, Compile, Run and Debug online from anywhere in world.

*******************************************************************************/

package main

import (

    "fmt"

    "errors"

    "encoding/json"

)


type MHREQIF interface {

    ProcessRequest(e int) (interface{}, error)

}


type MHRSP struct {

    Success bool `json:"success,omitempty"`

    ErrorMessage string `json:"error_message,omitempty"`

}


type FooReq struct {

    MHREQIF

    Name string `json:"name"`

}


type FooRsp struct {

    MHRSP

    Name string `json:"name"`

}


func (self *FooReq) ProcessRequest(e int) (interface{}, error) {

    rsp := FooRsp{Name:self.Name}

    if 0 == e {

        return &rsp, nil    

    } else {

        return &rsp, errors.New("crap")

    }

}


func main() {

    var msg_req MHREQIF

    msg_req = &FooReq{Name:"bob"}

    rsp, err := msg_req.ProcessRequest(1)

    if err != nil {

        // -------------- PROBLEM AREA BEG ------------------

        v := rsp.(MHRSP)

        v.Success = false

        v.ErrorMessage = fmt.Sprintf("%v", err)

        // -------------- PROBLEM AREA END ------------------

    }

    msg_bytes, _ := json.Marshal(rsp)

    msg_string := string(msg_bytes)

    fmt.Println(msg_string)

}


侃侃无极
浏览 136回答 1
1回答

慕田峪7331174

有时从 C++ OO 到 go-isms 的转变令人费解:P这是任何在如何解决此类问题上遇到类似困难的人的工作代码。/******************************************************************************Welcome to GDB Online.GDB online is an online compiler and debugger tool for C, C++, Python, Java, PHP, Ruby, Perl,C#, VB, Swift, Pascal, Fortran, Haskell, Objective-C, Assembly, HTML, CSS, JS, SQLite, Prolog.Code, Compile, Run and Debug online from anywhere in world.https://www.onlinegdb.com/online_c++_compiler*******************************************************************************/package mainimport (    "fmt"    "errors"    "encoding/json")type MHREQIF interface {    ProcessRequest(e int) (MHRESPIF, error)}type MHRESPIF interface {    SetResponse(err error)}type MHRSP struct {    MHRESPIF `json:"-"`    Success bool `json:"success"`    ErrorMessage string `json:"error_message,omitempty"`}type FooReq struct {    MHREQIF    Name string `json:"name"`}type FooRsp struct {    MHRSP    Name string `json:"name"`}func (self *MHRSP) SetResponse(err error) {    if err != nil {        self.Success = false        self.ErrorMessage = fmt.Sprintf("%v", err)    } else {        self.Success = true    }}func (self *FooReq) ProcessRequest(e int) (MHRESPIF, error) {    rsp := FooRsp{Name:self.Name}    if 0 == e {        return &rsp, nil        } else {        return &rsp, errors.New("crap")    }}func main() {    var msg_req MHREQIF    msg_req = &FooReq{Name:"bob"}    rsp, err := msg_req.ProcessRequest(1)    rsp.SetResponse(err)    msg_bytes, _ := json.Marshal(rsp)    msg_string := string(msg_bytes)    fmt.Println(msg_string)}
随时随地看视频慕课网APP

相关分类

Go
我要回答