func SimulateMsgVote(ak AccountKeeper, k Keeper) simtypes.Operation {
	return operationSimulateMsgVote(ak, k, simtypes.Account{}, -1)
}
SimulateMsgVote generates a MsgVote with random values.
package gov
import (
	"math"
	"math/rand"
	"time"
	"github.com/Dipper-Labs/Dipper-Protocol/app/simapp/helpers"
	simappparams "github.com/Dipper-Labs/Dipper-Protocol/app/simapp/params"
	"github.com/Dipper-Labs/Dipper-Protocol/app/v0/gov/types"
	"github.com/Dipper-Labs/Dipper-Protocol/app/v0/simulation"
	"github.com/Dipper-Labs/Dipper-Protocol/baseapp"
	"github.com/Dipper-Labs/Dipper-Protocol/codec"
	sdk "github.com/Dipper-Labs/Dipper-Protocol/types"
	simtypes "github.com/Dipper-Labs/Dipper-Protocol/types/simulation"
)
var initialProposalID = uint64(100000000000000)
const (
	OpWeightMsgDeposit = "op_weight_msg_deposit"
	OpWeightMsgVote    = "op_weight_msg_vote"
)
func WeightedOperations(
	appParams simtypes.AppParams,
	cdc *codec.Codec,
	ak AccountKeeper,
	k Keeper,
	wContents []simtypes.WeightedProposalContent) simulation.WeightedOperations {
	var (
		weightMsgDeposit int
		weightMsgVote    int
	)
	appParams.GetOrGenerate(cdc, OpWeightMsgDeposit, &weightMsgDeposit, nil,
		func(_ *rand.Rand) {
			weightMsgDeposit = simappparams.DefaultWeightMsgDeposit
		},
	)
	appParams.GetOrGenerate(cdc, OpWeightMsgVote, &weightMsgVote, nil,
		func(_ *rand.Rand) {
			weightMsgVote = simappparams.DefaultWeightMsgVote
		},
	)
	var wProposalOps simulation.WeightedOperations
	for _, wContent := range wContents {
		wContent := wContent  
		var weight int
		appParams.GetOrGenerate(cdc, wContent.AppParamsKey(), &weight, nil,
			func(_ *rand.Rand) { weight = wContent.DefaultWeight() })
		wProposalOps = append(
			wProposalOps,
			simulation.NewWeightedOperation(
				weight,
				SimulateSubmitProposal(ak, k, wContent.ContentSimulatorFn()),
			),
		)
	}
	wGovOps := simulation.WeightedOperations{
		simulation.NewWeightedOperation(
			weightMsgDeposit,
			SimulateMsgDeposit(ak, k),
		),
		simulation.NewWeightedOperation(
			weightMsgVote,
			SimulateMsgVote(ak, k),
		),
	}
	return append(wProposalOps, wGovOps...)
}
func SimulateSubmitProposal(ak AccountKeeper, k Keeper, contentSim simtypes.ContentSimulatorFn) simtypes.Operation {
	numVotesTransitionMatrix, _ := simulation.CreateTransitionMatrix([][]int{
		{20, 10, 0, 0, 0, 0},
		{55, 50, 20, 10, 0, 0},
		{25, 25, 30, 25, 30, 15},
		{0, 15, 30, 25, 30, 30},
		{0, 0, 20, 30, 30, 30},
		{0, 0, 0, 10, 10, 25},
	})
	statePercentageArray := []float64{1, .9, .75, .4, .15, 0}
	curNumVotesState := 1
	return func(r *rand.Rand, app interface{}, ctx sdk.Context, accs []simtypes.Account, chainID string) (simtypes.OperationMsg, []simtypes.FutureOperation, error) {
		a := baseapp.DereferenceBaseApp(app)
		if a == nil {
			return simtypes.NoOpMsg(types.ModuleName, types.TypeMsgSubmitProposal, "app invalid"), nil, nil
		}
		content := contentSim(r, ctx, accs)
		if content == nil {
			return simtypes.NoOpMsg(types.ModuleName, types.TypeMsgSubmitProposal, "content is nil"), nil, nil
		}
		simAccount, _ := simtypes.RandomAcc(r, accs)
		deposit, skip, err := randomDeposit(r, ctx, ak, k, simAccount.Address)
		switch {
		case skip:
			return simtypes.NoOpMsg(types.ModuleName, types.TypeMsgSubmitProposal, "skip deposit"), nil, nil
		case err != nil:
			return simtypes.NoOpMsg(types.ModuleName, types.TypeMsgSubmitProposal, "unable to generate deposit"), nil, err
		}
		msg := types.NewMsgSubmitProposal(content, deposit, simAccount.Address)
		account := ak.GetAccount(ctx, simAccount.Address)
		spendable := account.GetCoins()
		var fees sdk.Coins
		coins, hasNeg := spendable.SafeSub(deposit)
		if !hasNeg {
			fees, err = simtypes.RandomFees(r, ctx, coins)
			if err != nil {
				return simtypes.NoOpMsg(types.ModuleName, msg.Type(), "unable to generate fees"), nil, err
			}
		}
		tx := helpers.GenTx(
			[]sdk.Msg{msg},
			fees,
			helpers.DefaultGenTxGas,
			chainID,
			[]uint64{account.GetAccountNumber()},
			[]uint64{account.GetSequence()},
			simAccount.PrivKey,
		)
		_, _, err = a.Deliver(tx)
		if err != nil {
			return simtypes.NoOpMsg(types.ModuleName, msg.Type(), "unable to deliver tx"), nil, err
		}
		opMsg := simtypes.NewOperationMsg(msg, true, "")
		proposalID, err := k.GetProposalID(ctx)
		if err != nil {
			return simtypes.NoOpMsg(types.ModuleName, msg.Type(), "unable to generate proposalID"), nil, err
		}
		curNumVotesState = numVotesTransitionMatrix.NextState(r, curNumVotesState)
		numVotes := int(math.Ceil(float64(len(accs)) * statePercentageArray[curNumVotesState]))
		whoVotes := r.Perm(len(accs))
		whoVotes = whoVotes[:numVotes]
		votingPeriod := k.GetVotingParams(ctx).VotingPeriod
		fops := make([]simtypes.FutureOperation, numVotes+1)
		for i := 0; i < numVotes; i++ {
			whenVote := ctx.BlockHeader().Time.Add(time.Duration(r.Int63n(int64(votingPeriod.Seconds()))) * time.Second)
			fops[i] = simtypes.FutureOperation{
				BlockTime: whenVote,
				Op:        operationSimulateMsgVote(ak, k, accs[whoVotes[i]], int64(proposalID)),
			}
		}
		return opMsg, fops, nil
	}
}
func SimulateMsgDeposit(ak AccountKeeper, k Keeper) simtypes.Operation {
	return func(r *rand.Rand, app interface{}, ctx sdk.Context, accs []simtypes.Account, chainID string) (simtypes.OperationMsg, []simtypes.FutureOperation, error) {
		a := baseapp.DereferenceBaseApp(app)
		if a == nil {
			return simtypes.NoOpMsg(types.ModuleName, types.TypeMsgDeposit, "app invalid"), nil, nil
		}
		simAccount, _ := simtypes.RandomAcc(r, accs)
		proposalID, ok := randomProposalID(r, k, ctx, types.StatusDepositPeriod)
		if !ok {
			return simtypes.NoOpMsg(types.ModuleName, types.TypeMsgDeposit, "unable to generate proposalID"), nil, nil
		}
		deposit, skip, err := randomDeposit(r, ctx, ak, k, simAccount.Address)
		switch {
		case skip:
			return simtypes.NoOpMsg(types.ModuleName, types.TypeMsgDeposit, "skip deposit"), nil, nil
		case err != nil:
			return simtypes.NoOpMsg(types.ModuleName, types.TypeMsgDeposit, "unable to generate deposit"), nil, err
		}
		msg := types.NewMsgDeposit(simAccount.Address, proposalID, deposit)
		account := ak.GetAccount(ctx, simAccount.Address)
		spendable := account.GetCoins()
		var fees sdk.Coins
		coins, hasNeg := spendable.SafeSub(deposit)
		if !hasNeg {
			fees, err = simtypes.RandomFees(r, ctx, coins)
			if err != nil {
				return simtypes.NoOpMsg(types.ModuleName, msg.Type(), "unable to generate fees"), nil, err
			}
		}
		tx := helpers.GenTx(
			[]sdk.Msg{msg},
			fees,
			helpers.DefaultGenTxGas,
			chainID,
			[]uint64{account.GetAccountNumber()},
			[]uint64{account.GetSequence()},
			simAccount.PrivKey,
		)
		_, _, err = a.Deliver(tx)
		if err != nil {
			return simtypes.NoOpMsg(types.ModuleName, msg.Type(), "unable to deliver tx"), nil, err
		}
		return simtypes.NewOperationMsg(msg, true, ""), nil, nil
	}
}