func setWithProperType(t reflect.Type, key *Key, field reflect.Value, delim string) error {
	switch t.Kind() {
	case reflect.String:
		if len(key.String()) == 0 {
			return nil
		}
		field.SetString(key.String())
	case reflect.Bool:
		boolVal, err := key.Bool()
		if err != nil {
			return nil
		}
		field.SetBool(boolVal)
	case reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64:
		durationVal, err := key.Duration()
		if err == nil && int(durationVal) > 0 {
			field.Set(reflect.ValueOf(durationVal))
			return nil
		}
		intVal, err := key.Int64()
		if err != nil || intVal == 0 {
			return nil
		}
		field.SetInt(intVal)
	case reflect.Uint, reflect.Uint16, reflect.Uint32, reflect.Uint64:
		durationVal, err := key.Duration()
		if err == nil {
			field.Set(reflect.ValueOf(durationVal))
			return nil
		}
		uintVal, err := key.Uint64()
		if err != nil {
			return nil
		}
		field.SetUint(uintVal)
	case reflect.Float64:
		floatVal, err := key.Float64()
		if err != nil {
			return nil
		}
		field.SetFloat(floatVal)
	case reflectTime:
		timeVal, err := key.Time()
		if err != nil {
			return nil
		}
		field.Set(reflect.ValueOf(timeVal))
	case reflect.Slice:
		return setSliceWithProperType(key, field, delim)
	default:
		return fmt.Errorf("unsupported type '%s'", t)
	}
	return nil
}
setWithProperType sets proper value to field based on its type,
but it does not return error for failing parsing,
because we want to use default value that is already assigned to strcut.
package ini
import (
	"bytes"
	"errors"
	"fmt"
	"reflect"
	"time"
	"unicode"
)
type NameMapper func(string) string
var (
	AllCapsUnderscore NameMapper = func(raw string) string {
		newstr := make([]rune, 0, len(raw))
		for i, chr := range raw {
			if isUpper := 'A' <= chr && chr <= 'Z'; isUpper {
				if i > 0 {
					newstr = append(newstr, '_')
				}
			}
			newstr = append(newstr, unicode.ToUpper(chr))
		}
		return string(newstr)
	}
	TitleUnderscore NameMapper = func(raw string) string {
		newstr := make([]rune, 0, len(raw))
		for i, chr := range raw {
			if isUpper := 'A' <= chr && chr <= 'Z'; isUpper {
				if i > 0 {
					newstr = append(newstr, '_')
				}
				chr -= ('A' - 'a')
			}
			newstr = append(newstr, chr)
		}
		return string(newstr)
	}
)
func (s *Section) parseFieldName(raw, actual string) string {
	if len(actual) > 0 {
		return actual
	}
	if s.f.NameMapper != nil {
		return s.f.NameMapper(raw)
	}
	return raw
}
func parseDelim(actual string) string {
	if len(actual) > 0 {
		return actual
	}
	return ","
}
var reflectTime = reflect.TypeOf(time.Now()).Kind()
func setSliceWithProperType(key *Key, field reflect.Value, delim string) error {
	strs := key.Strings(delim)
	numVals := len(strs)
	if numVals == 0 {
		return nil
	}
	var vals interface{}
	sliceOf := field.Type().Elem().Kind()
	switch sliceOf {
	case reflect.String:
		vals = strs
	case reflect.Int:
		vals = key.Ints(delim)
	case reflect.Int64:
		vals = key.Int64s(delim)
	case reflect.Uint:
		vals = key.Uints(delim)
	case reflect.Uint64:
		vals = key.Uint64s(delim)
	case reflect.Float64:
		vals = key.Float64s(delim)
	case reflectTime:
		vals = key.Times(delim)
	default:
		return fmt.Errorf("unsupported type '[]%s'", sliceOf)
	}
	slice := reflect.MakeSlice(field.Type(), numVals, numVals)
	for i := 0; i < numVals; i++ {
		switch sliceOf {
		case reflect.String:
			slice.Index(i).Set(reflect.ValueOf(vals.([]string)[i]))
		case reflect.Int:
			slice.Index(i).Set(reflect.ValueOf(vals.([]int)[i]))
		case reflect.Int64:
			slice.Index(i).Set(reflect.ValueOf(vals.([]int64)[i]))
		case reflect.Uint:
			slice.Index(i).Set(reflect.ValueOf(vals.([]uint)[i]))
		case reflect.Uint64:
			slice.Index(i).Set(reflect.ValueOf(vals.([]uint64)[i]))
		case reflect.Float64:
			slice.Index(i).Set(reflect.ValueOf(vals.([]float64)[i]))
		case reflectTime:
			slice.Index(i).Set(reflect.ValueOf(vals.([]time.Time)[i]))
		}
	}
	field.Set(slice)
	return nil
}